<!DOCTYPE html>
<html lang="en-US">
  <head>
    <meta charset="utf-8">
    <meta name="viewport" content="width=device-width,initial-scale=1">
    <title>1-6 JavaScript进阶学习笔记 | HasakWebBlog</title>
    <meta name="generator" content="VuePress 1.9.7">
    <link rel="icon" href="/favicon.ico">
    <meta name="description" content="hasak">
    <meta name="viewport" content="width=device-width,initial-scale=1,user-scalable=no">
    
    <link rel="preload" href="/assets/css/0.styles.a5a0d673.css" as="style"><link rel="preload" href="/assets/js/app.c7915c77.js" as="script"><link rel="preload" href="/assets/js/3.f80332a6.js" as="script"><link rel="preload" href="/assets/js/1.5cffa4a1.js" as="script"><link rel="preload" href="/assets/js/32.098b21df.js" as="script"><link rel="prefetch" href="/assets/js/10.02ae8499.js"><link rel="prefetch" href="/assets/js/11.c5238d8f.js"><link rel="prefetch" href="/assets/js/12.be21fd80.js"><link rel="prefetch" href="/assets/js/13.bd684308.js"><link rel="prefetch" href="/assets/js/14.b5f9fc77.js"><link rel="prefetch" href="/assets/js/15.318683dc.js"><link rel="prefetch" href="/assets/js/16.74f9d94e.js"><link rel="prefetch" href="/assets/js/17.cd1e6d69.js"><link rel="prefetch" href="/assets/js/18.901e5492.js"><link rel="prefetch" href="/assets/js/19.417d2070.js"><link rel="prefetch" href="/assets/js/20.39ec66a2.js"><link rel="prefetch" href="/assets/js/21.fbf1aaf8.js"><link rel="prefetch" href="/assets/js/22.736aeb98.js"><link rel="prefetch" href="/assets/js/23.abcdc310.js"><link rel="prefetch" href="/assets/js/24.26658596.js"><link rel="prefetch" href="/assets/js/25.40bdc691.js"><link rel="prefetch" href="/assets/js/26.29ac009b.js"><link rel="prefetch" href="/assets/js/27.edc6afbf.js"><link rel="prefetch" href="/assets/js/28.b9c1065e.js"><link rel="prefetch" href="/assets/js/29.b46f8f9e.js"><link rel="prefetch" href="/assets/js/30.6839ae7e.js"><link rel="prefetch" href="/assets/js/31.85913f4e.js"><link rel="prefetch" href="/assets/js/33.faced894.js"><link rel="prefetch" href="/assets/js/34.239b19e7.js"><link rel="prefetch" href="/assets/js/35.5c8a8406.js"><link rel="prefetch" href="/assets/js/36.46f0ebac.js"><link rel="prefetch" href="/assets/js/37.2456f410.js"><link rel="prefetch" href="/assets/js/38.b76624ee.js"><link rel="prefetch" href="/assets/js/39.64ecef14.js"><link rel="prefetch" href="/assets/js/4.7d7a493e.js"><link rel="prefetch" href="/assets/js/40.a1304a44.js"><link rel="prefetch" href="/assets/js/41.f98208ce.js"><link rel="prefetch" href="/assets/js/42.f0be4a4c.js"><link rel="prefetch" href="/assets/js/43.1a46f61e.js"><link rel="prefetch" href="/assets/js/44.d579b00f.js"><link rel="prefetch" href="/assets/js/45.8e8ea47a.js"><link rel="prefetch" href="/assets/js/46.1b194721.js"><link rel="prefetch" href="/assets/js/47.994c7d71.js"><link rel="prefetch" href="/assets/js/48.f17a641c.js"><link rel="prefetch" href="/assets/js/49.0d9ea06f.js"><link rel="prefetch" href="/assets/js/5.176296fc.js"><link rel="prefetch" href="/assets/js/50.e36885a9.js"><link rel="prefetch" href="/assets/js/51.64538ee2.js"><link rel="prefetch" href="/assets/js/52.1fd24c2e.js"><link rel="prefetch" href="/assets/js/53.967b1458.js"><link rel="prefetch" href="/assets/js/54.05b15a98.js"><link rel="prefetch" href="/assets/js/55.3c78b9d4.js"><link rel="prefetch" href="/assets/js/56.8d130c30.js"><link rel="prefetch" href="/assets/js/57.0008c022.js"><link rel="prefetch" href="/assets/js/58.4b49a382.js"><link rel="prefetch" href="/assets/js/59.8bb182dc.js"><link rel="prefetch" href="/assets/js/6.90835ce9.js"><link rel="prefetch" href="/assets/js/60.93235335.js"><link rel="prefetch" href="/assets/js/61.78370acd.js"><link rel="prefetch" href="/assets/js/62.1144f314.js"><link rel="prefetch" href="/assets/js/63.7fb72cd2.js"><link rel="prefetch" href="/assets/js/64.de8ba1be.js"><link rel="prefetch" href="/assets/js/65.cefa274d.js"><link rel="prefetch" href="/assets/js/66.32ad44bf.js"><link rel="prefetch" href="/assets/js/67.558c356c.js"><link rel="prefetch" href="/assets/js/68.15a3af19.js"><link rel="prefetch" href="/assets/js/69.b1b26c0a.js"><link rel="prefetch" href="/assets/js/7.2c075495.js"><link rel="prefetch" href="/assets/js/70.cb9b8e94.js"><link rel="prefetch" href="/assets/js/71.e371986a.js"><link rel="prefetch" href="/assets/js/72.a8af9117.js"><link rel="prefetch" href="/assets/js/73.dcc5a1af.js"><link rel="prefetch" href="/assets/js/74.803a909b.js"><link rel="prefetch" href="/assets/js/75.8129f8f6.js"><link rel="prefetch" href="/assets/js/76.ffcb07fc.js"><link rel="prefetch" href="/assets/js/8.9b4cfefe.js"><link rel="prefetch" href="/assets/js/9.e529cf11.js">
    <link rel="stylesheet" href="/assets/css/0.styles.a5a0d673.css">
  </head>
  <body>
    <div id="app" data-server-rendered="true"><div class="theme-container" data-v-7dd95ae2><div data-v-7dd95ae2><div class="password-shadow password-wrapper-out" style="display:none;" data-v-59e6cb88 data-v-7dd95ae2 data-v-7dd95ae2><h3 class="title" data-v-59e6cb88>HasakWebBlog</h3> <p class="description" data-v-59e6cb88>hasak</p> <label id="box" class="inputBox" data-v-59e6cb88><input type="password" value="" data-v-59e6cb88> <span data-v-59e6cb88>Konck! Knock!</span> <button data-v-59e6cb88>OK</button></label> <div class="footer" data-v-59e6cb88><span data-v-59e6cb88><i class="iconfont reco-theme" data-v-59e6cb88></i> <a target="blank" href="https://vuepress-theme-reco.recoluan.com" data-v-59e6cb88>vuePress-theme-reco</a></span> <span data-v-59e6cb88><i class="iconfont reco-copyright" data-v-59e6cb88></i> <a data-v-59e6cb88><span data-v-59e6cb88>hasak</span>
          
        <span data-v-59e6cb88>2022 - </span>
        2023
      </a></span></div></div> <div class="hide" data-v-7dd95ae2><header class="navbar" data-v-7dd95ae2><div class="sidebar-button"><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" role="img" viewBox="0 0 448 512" class="icon"><path fill="currentColor" d="M436 124H12c-6.627 0-12-5.373-12-12V80c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12zm0 160H12c-6.627 0-12-5.373-12-12v-32c0-6.627 5.373-12 12-12h424c6.627 0 12 5.373 12 12v32c0 6.627-5.373 12-12 12z"></path></svg></div> <a href="/" class="home-link router-link-active"><img src="/logo.png" alt="HasakWebBlog" class="logo"> <span class="site-name">HasakWebBlog</span></a> <div class="links"><div class="color-picker"><a class="color-button"><i class="iconfont reco-color"></i></a> <div class="color-picker-menu" style="display:none;"><div class="mode-options"><h4 class="title">Choose mode</h4> <ul class="color-mode-options"><li class="dark">dark</li><li class="auto active">auto</li><li class="light">light</li></ul></div></div></div> <div class="search-box"><i class="iconfont reco-search"></i> <input aria-label="Search" autocomplete="off" spellcheck="false" value=""> <!----></div> <nav class="nav-links can-hide"><div class="nav-item"><a href="/" class="nav-link"><i class="iconfont reco-home"></i>
  Home
</a></div><div class="nav-item"><div class="dropdown-wrapper"><a class="dropdown-title"><span class="title"><i class="iconfont reco-category"></i>
      前端学习
    </span> <span class="arrow right"></span></a> <ul class="nav-dropdown" style="display:none;"><li class="dropdown-item"><!----> <a href="/categories/HTML5&amp;CSS3/" class="nav-link"><i class="undefined"></i>
  HTML5&amp;CSS3
</a></li><li class="dropdown-item"><!----> <a href="/categories/Javascript/" class="nav-link"><i class="undefined"></i>
  Javascript
</a></li><li class="dropdown-item"><!----> <a href="/categories/Node/" class="nav-link"><i class="undefined"></i>
  Node
</a></li><li class="dropdown-item"><!----> <a href="/categories/VUE/" class="nav-link"><i class="undefined"></i>
  VUE
</a></li></ul></div></div><div class="nav-item"><a href="/tag/" class="nav-link"><i class="iconfont reco-tag"></i>
  Tags
</a></div><div class="nav-item"><a href="/timeline/" class="nav-link"><i class="iconfont reco-date"></i>
  时间轴
</a></div><div class="nav-item"><div class="dropdown-wrapper"><a class="dropdown-title"><span class="title"><i class="iconfont reco-message"></i>
      联系我
    </span> <span class="arrow right"></span></a> <ul class="nav-dropdown" style="display:none;"><li class="dropdown-item"><!----> <a href="https://github.com/hasakxu" target="_blank" rel="noopener noreferrer" class="nav-link external"><i class="iconfont reco-github"></i>
  GitHub
  <span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></li></ul></div></div> <!----></nav></div></header> <div class="sidebar-mask" data-v-7dd95ae2></div> <aside class="sidebar" data-v-7dd95ae2><div class="personal-info-wrapper" data-v-1fad0c41 data-v-7dd95ae2><img src="/dog.png" alt="author-avatar" class="personal-img" data-v-1fad0c41> <h3 class="name" data-v-1fad0c41>
    hasak
  </h3> <div class="num" data-v-1fad0c41><div data-v-1fad0c41><h3 data-v-1fad0c41>66</h3> <h6 data-v-1fad0c41>Articles</h6></div> <div data-v-1fad0c41><h3 data-v-1fad0c41>5</h3> <h6 data-v-1fad0c41>Tags</h6></div></div> <ul class="social-links" data-v-1fad0c41></ul> <hr data-v-1fad0c41></div> <nav class="nav-links"><div class="nav-item"><a href="/" class="nav-link"><i class="iconfont reco-home"></i>
  Home
</a></div><div class="nav-item"><div class="dropdown-wrapper"><a class="dropdown-title"><span class="title"><i class="iconfont reco-category"></i>
      前端学习
    </span> <span class="arrow right"></span></a> <ul class="nav-dropdown" style="display:none;"><li class="dropdown-item"><!----> <a href="/categories/HTML5&amp;CSS3/" class="nav-link"><i class="undefined"></i>
  HTML5&amp;CSS3
</a></li><li class="dropdown-item"><!----> <a href="/categories/Javascript/" class="nav-link"><i class="undefined"></i>
  Javascript
</a></li><li class="dropdown-item"><!----> <a href="/categories/Node/" class="nav-link"><i class="undefined"></i>
  Node
</a></li><li class="dropdown-item"><!----> <a href="/categories/VUE/" class="nav-link"><i class="undefined"></i>
  VUE
</a></li></ul></div></div><div class="nav-item"><a href="/tag/" class="nav-link"><i class="iconfont reco-tag"></i>
  Tags
</a></div><div class="nav-item"><a href="/timeline/" class="nav-link"><i class="iconfont reco-date"></i>
  时间轴
</a></div><div class="nav-item"><div class="dropdown-wrapper"><a class="dropdown-title"><span class="title"><i class="iconfont reco-message"></i>
      联系我
    </span> <span class="arrow right"></span></a> <ul class="nav-dropdown" style="display:none;"><li class="dropdown-item"><!----> <a href="https://github.com/hasakxu" target="_blank" rel="noopener noreferrer" class="nav-link external"><i class="iconfont reco-github"></i>
  GitHub
  <span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></li></ul></div></div> <!----></nav> <ul class="sidebar-links"><li><section class="sidebar-group collapsable depth-0"><p class="sidebar-heading open"><span>Javascript 学习</span> <span class="arrow down"></span></p> <ul class="sidebar-links sidebar-group-items"><li><a href="/blogs/基础/js/20221113js01.html" class="sidebar-link">1-1 介绍、变量、数据类型、类型转换</a></li><li><a href="/blogs/基础/js/20221113js02.html" class="sidebar-link">1-2 运算符 流程控制语句</a></li><li><a href="/blogs/基础/js/20221114js03.html" class="sidebar-link">1-3 数组 函数</a></li><li><a href="/blogs/基础/js/20221114js04.html" class="sidebar-link">1-4 作用域 与解析 对象</a></li><li><a href="/blogs/基础/js/20221114js05.html" class="sidebar-link">1-5 内置对象 简单类型与复杂类型</a></li><li><a href="/blogs/基础/js/20221114js06.html" class="active sidebar-link">1-6 JavaScript进阶学习笔记</a></li><li><a href="/blogs/基础/js/20221114js07.html" class="sidebar-link">2-1 Web APIs 简介 DOM</a></li><li><a href="/blogs/基础/js/20221114js08.html" class="sidebar-link">2-2 事件高级</a></li><li><a href="/blogs/基础/js/20221114js09.html" class="sidebar-link">2-3 BOM 浏览器对象模型</a></li><li><a href="/blogs/基础/js/20221114js10.html" class="sidebar-link">2-4 网页特效</a></li><li><a href="/blogs/基础/js/20221114js11.html" class="sidebar-link">2-5 本地存储</a></li><li><a href="/blogs/基础/js/20221116js12.html" class="sidebar-link">3-1 jQuery 入门</a></li><li><a href="/blogs/基础/js/20221116js13.html" class="sidebar-link">3-2 jQuery 常用API</a></li><li><a href="/blogs/基础/js/20221116js14.html" class="sidebar-link">3-3 jQuery 事件 其他方法</a></li><li><a href="/blogs/基础/js/20221116js15.html" class="sidebar-link">4 AJAX</a></li><li><a href="/blogs/基础/js/20221116js16.html" class="sidebar-link">5 ES6</a></li></ul></section></li></ul> </aside> <div class="password-shadow password-wrapper-in" style="display:none;" data-v-59e6cb88 data-v-7dd95ae2><h3 class="title" data-v-59e6cb88>1-6 JavaScript进阶学习笔记</h3> <!----> <label id="box" class="inputBox" data-v-59e6cb88><input type="password" value="" data-v-59e6cb88> <span data-v-59e6cb88>Konck! Knock!</span> <button data-v-59e6cb88>OK</button></label> <div class="footer" data-v-59e6cb88><span data-v-59e6cb88><i class="iconfont reco-theme" data-v-59e6cb88></i> <a target="blank" href="https://vuepress-theme-reco.recoluan.com" data-v-59e6cb88>vuePress-theme-reco</a></span> <span data-v-59e6cb88><i class="iconfont reco-copyright" data-v-59e6cb88></i> <a data-v-59e6cb88><span data-v-59e6cb88>hasak</span>
          
        <span data-v-59e6cb88>2022 - </span>
        2023
      </a></span></div></div> <div data-v-7dd95ae2><div data-v-7dd95ae2><main class="page" style="padding-right:0;"><section style="display:;"><div class="page-title"><h1 class="title">1-6 JavaScript进阶学习笔记</h1> <div data-v-8a445198><i class="iconfont reco-account" data-v-8a445198><span data-v-8a445198>hasak</span></i> <i class="iconfont reco-date" data-v-8a445198><span data-v-8a445198>6/20/2022</span></i> <!----> <i class="tags iconfont reco-tag" data-v-8a445198><span class="tag-item" data-v-8a445198>JS</span></i></div></div> <div class="theme-reco-content content__default"><h1 id="_1-6-javascript进阶学习笔记"><a href="#_1-6-javascript进阶学习笔记" class="header-anchor">#</a> 1-6 JavaScript进阶学习笔记</h1> <h2 id="转载"><a href="#转载" class="header-anchor">#</a> 转载</h2> <blockquote><p>此笔记为JavaScript进阶学习笔记，会对之前javaScript基础做一次梳理，并进行对于其进阶知识进行学习与记录</p> <p>借阅以及参照学习资料:B站尚硅谷的<a href="https://gitee.com/link?target=https%3A%2F%2Fwww.bilibili.com%2Fvideo%2FBV14s411E7qf%3Fshare_source%3Dcopy_web" target="_blank" rel="noopener noreferrer">尚硅谷JavaScript高级教程(javascript实战进阶)<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、黑马程序员的[<a href="https://gitee.com/link?target=https%3A%2F%2Fwww.bilibili.com%2Fvideo%2FBV1ux411d75J%3Fshare_source%3Dcopy_web" target="_blank" rel="noopener noreferrer">JavaScript基础语法<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>];印记中文的<a href="https://gitee.com/link?target=https%3A%2F%2Fzh.javascript.info%2F" target="_blank" rel="noopener noreferrer">现在JavaScript教程<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>; CSDN的<a href="https://gitee.com/link?target=https%3A%2F%2Fblog.csdn.net%2Fwangfeijiu" target="_blank" rel="noopener noreferrer">Free Joe的JS执行过程与执行上下文（栈）<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>;FunDebug的<a href="https://gitee.com/link?target=https%3A%2F%2Fblog.fundebug.com%2F2019%2F02%2F12%2Funderstand-javascript-closure%2F" target="_blank" rel="noopener noreferrer">我从来不理解 JavaScript 闭包，直到有人这样向我解释它...<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>;知乎的<a href="https://gitee.com/link?target=https%3A%2F%2Fzhuanlan.zhihu.com%2Fp%2F33058983" target="_blank" rel="noopener noreferrer">详解JavaScript中的Event Loop（事件循环）机制<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></p> <p>除此笔记外大家可以看我其他笔记 :<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master" target="_blank" rel="noopener noreferrer">全栈笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E7%AE%97%E6%B3%95%E5%8F%8A%E8%AF%BE%E7%A8%8B%E5%9F%BA%E7%A1%80%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/%E6%95%B0%E6%8D%AE%E7%BB%93%E6%9E%84%E4%B8%8E%E7%AE%97%E6%B3%95" target="_blank" rel="noopener noreferrer">数据结构与算法<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">编程_前端开发学习笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%90%8E%E5%8F%B0%E6%9C%8D%E5%8A%A1%E7%AB%AF%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/Nodejs" target="_blank" rel="noopener noreferrer">Nodejs<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/HTML+CSS+JS%E5%9F%BA%E7%A1%80%E7%AC%94%E8%AE%B0/JavaScript%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">JavaScript笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/A_%E5%89%8D%E7%AB%AF%E5%B7%A5%E5%85%B7%E4%BD%BF%E7%94%A8%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">编程工具使用笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/ES6%E5%8F%8A%E5%90%8E%E7%BB%AD%E7%89%88%E6%9C%AC%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">ES6及后续版本学习笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/Vue%E7%AC%94%E8%AE%B0%E6%95%B4%E5%90%88" target="_blank" rel="noopener noreferrer">Vue笔记整合<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/React%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">React笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/%E5%BE%AE%E4%BF%A1%E5%B0%8F%E7%A8%8B%E5%BA%8F%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">微信小程序学习笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>、<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/Chrome%E5%BC%80%E5%8F%91%E4%BD%BF%E7%94%A8%E5%8F%8A%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">Chrome开发使用及学习笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 以及许多其他笔记就不一一例举了</p> <p>此处强烈建议同学们学完 JavaScript 不要急着去学 NodeJS 或者 VUE 框架 ,一定要先学 <code>ES系列</code> 现在基本上都用的ES6以及后续写法开发了, 你不学基本上也是看不懂别人代码的, 这已经成了前端基本功了 --&gt; <a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/ES6%E5%8F%8A%E5%90%8E%E7%BB%AD%E7%89%88%E6%9C%AC%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0" target="_blank" rel="noopener noreferrer">ES6及后续版本学习笔记<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></p></blockquote> <h2 id="一、-javascript基础总结"><a href="#一、-javascript基础总结" class="header-anchor">#</a> 一、 JavaScript基础总结</h2> <h3 id="_1-1-数据类型相关知识点"><a href="#_1-1-数据类型相关知识点" class="header-anchor">#</a> 1.1 数据类型相关知识点</h3> <p><strong>Ⅰ-基本(值)类型</strong></p> <ol><li><code>String</code> 任意字符串</li> <li><code>Number</code> 任意数字</li> <li><code>Boolean</code> true/false</li> <li><code>Undefined</code> 值为undefined</li> <li><code>Null</code> null --&gt;使用typeof时返回<code>object</code></li> <li><a href="https://developer.mozilla.org/zh-CN/docs/Glossary/Symbol" target="_blank" rel="noopener noreferrer">Symbol<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>（<a href="https://developer.mozilla.org/zh-CN/docs/Glossary/ECMAScript" target="_blank" rel="noopener noreferrer">ECMAScript<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 2016新增）---&gt;Symbol 是 <a href="https://developer.mozilla.org/zh-CN/docs/Glossary/Primitive" target="_blank" rel="noopener noreferrer">基本数据类型<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 的一种，symbol 对象是 Symbol 原始值的<a href="https://gitee.com/link?target=https%3A%2F%2Fdeveloper.mozilla.org%2Fen-US%2Fdocs%2FGlossary%2FWrapper" target="_blank" rel="noopener noreferrer">封装 (en-US)<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></li> <li><a href="https://gitee.com/link?target=https%3A%2F%2Fdeveloper.mozilla.org%2Fzh-CN%2Fdocs%2FGlossary%2FBigInt" target="_blank" rel="noopener noreferrer">Bigint<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>， --&gt;BigInt 是一种数字类型的数据，它可以表示任意精度格式的整数
加上下方的 [ 对象 ] 类型,目前 javaScript 有八种数据类型</li></ol> <p><strong>Ⅱ-对象(引用)类型</strong></p> <ol><li>Object: 任意对象</li> <li>Function: 一种特别的对象（可以执行）--- 内部包含可运行的代码</li> <li>Array: 一种特别的对象（key 为数值下标属性, 内部数据是有序的）</li></ol> <p><strong>Ⅲ-判断方法</strong></p> <p><font color="#d00">1. <code>typeof</code></font></p> <p>操作符返回一个<font color="#d00">字符串</font>，表示未经计算的操作数的类型</p> <ul><li>可以判断: undefined/ 数值 / 字符串 / 布尔值 / function</li> <li>不能判断: null与object object与array</li> <li><strong>注意:</strong> 运行<code>console.log(typeof undefined)</code>时,得到的的也是一个<code>字符串</code>,<code>同时为小写!!--&gt; 'undefined'</code></li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// typeof返回数据类型的字符串表达</span>
<span class="token keyword">var</span> a
 
<span class="token comment">//注意:typeof返回的是字符串</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">,</span> <span class="token keyword">typeof</span> a<span class="token punctuation">,</span> <span class="token keyword">typeof</span> a<span class="token operator">=</span><span class="token string">'undefined'</span><span class="token punctuation">,</span>a<span class="token operator">=</span> <span class="token string">'undefined'</span><span class="token punctuation">)</span> <span class="token comment">//false</span>
a <span class="token operator">=</span> <span class="token number">4</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token operator">=</span><span class="token keyword">undefined</span> <span class="token punctuation">)</span>  <span class="token comment">// undefined 'undefined' true true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">undefined</span> <span class="token operator">=</span><span class="token string">'number'</span><span class="token punctuation">)</span> <span class="token comment">//true</span>
a <span class="token operator">=</span> <span class="token string">'hasakxu'</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token operator">=</span><span class="token string">'string'</span><span class="token punctuation">)</span> <span class="token comment">//true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token operator">=</span><span class="token string">'String'</span><span class="token punctuation">)</span> <span class="token comment">//false  --&gt;注意,返回的类型为小写</span>
a <span class="token operator">=</span> <span class="token boolean">true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token operator">===</span><span class="token string">'boolean'</span><span class="token punctuation">)</span> <span class="token comment">//true</span>
a <span class="token operator">=</span> <span class="token keyword">null</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token punctuation">,</span> a<span class="token operator">===</span><span class="token keyword">null</span><span class="token punctuation">)</span> <span class="token comment">// 'object'  true</span>
<span class="token keyword">let</span> b<span class="token operator">=</span><span class="token punctuation">{</span><span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> b<span class="token punctuation">,</span><span class="token keyword">typeof</span> <span class="token keyword">null</span><span class="token punctuation">,</span> <span class="token string">'-------'</span><span class="token punctuation">)</span> <span class="token comment">// 'object' 'object'  --&gt;所以Typeof不能判断null与object</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br></div></div><p><font color="#d00">2. <code>instanceof</code></font>(判断实例方法)</p> <ul><li><p><code>专门判断对象</code>的具体类型</p></li> <li><p><code>instanceof</code> 运算符用于检测构造函数的<code>prototype</code>属性是否出现在某个实例对象的原型链上。</p></li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token keyword">var</span> b1 <span class="token operator">=</span> <span class="token punctuation">{</span>
<span class="token literal-property property">b2</span><span class="token operator">:</span> <span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">,</span> <span class="token string">'abc'</span><span class="token punctuation">,</span> console<span class="token punctuation">.</span>log<span class="token punctuation">]</span><span class="token punctuation">,</span>
<span class="token comment">//可以简化成 b3:()=&gt;()=&gt; 'hasakxu'  --&gt;高阶函数相关知识</span>
<span class="token function-variable function">b3</span><span class="token operator">:</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
<span class="token keyword">return</span>  <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span><span class="token punctuation">{</span>  <span class="token keyword">return</span>   <span class="token string">'hasakxu'</span><span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token comment">/**使用instanceof进行对象判断*/</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b1 <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">,</span> b1 <span class="token keyword">instanceof</span> <span class="token class-name">Array</span><span class="token punctuation">)</span> <span class="token comment">// true  false</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b1<span class="token punctuation">.</span>b2 <span class="token keyword">instanceof</span> <span class="token class-name">Array</span><span class="token punctuation">,</span> b1<span class="token punctuation">.</span>b2 <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">)</span> <span class="token comment">// true true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b1<span class="token punctuation">.</span>b3 <span class="token keyword">instanceof</span> <span class="token class-name">Function</span><span class="token punctuation">,</span> b1<span class="token punctuation">.</span>b3 <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">)</span> <span class="token comment">// true true</span>
<span class="token comment">/**使用typeof进行对象中某属性的判断*/</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> b1<span class="token punctuation">.</span>b2<span class="token punctuation">,</span> <span class="token keyword">typeof</span> <span class="token keyword">null</span><span class="token punctuation">)</span> <span class="token comment">// 'object' 'object'</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> b1<span class="token punctuation">.</span>b3<span class="token operator">=</span><span class="token string">'function'</span><span class="token punctuation">)</span> <span class="token comment">// true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> b1<span class="token punctuation">.</span>b2<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token operator">=</span><span class="token string">'function'</span><span class="token punctuation">)</span> <span class="token comment">//true</span>
<span class="token comment">/**调用对象与数组中某函数示例*/</span>
b1<span class="token punctuation">.</span>b2<span class="token punctuation">[</span><span class="token number">2</span><span class="token punctuation">]</span><span class="token punctuation">(</span><span class="token string">'调用console.log打印hasakxu'</span><span class="token punctuation">)</span>    <span class="token comment">//调用console.log打印hasakxu</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b1<span class="token punctuation">.</span><span class="token function">b3</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token comment">// hasakxu</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br></div></div><p><font color="#d00">3. <code>===</code></font></p> <p>在比较两件事情时，双等号将执行类型转换后比较，三等号不进行类型转换，直接进行比较 (如果类型不同, 只是总会返回 false )
可以判断: undefined null，具体可以看 MDN的<a href="https://gitee.com/link?target=https%3A%2F%2Fdeveloper.mozilla.org%2Fzh-CN%2Fdocs%2FWeb%2FJavaScript%2FEquality_comparisons_and_sameness" target="_blank" rel="noopener noreferrer">JavaScript中的相等性判断<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></p> <p><strong>Ⅳ-相关问题引出</strong></p> <ol><li><strong>undefined 与 null 的区别?</strong> <ul><li><code>undefined</code>代表定义未赋值</li> <li><code>null</code>定义并赋值了, 只是值为<code>null</code></li></ul></li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> a
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>  <span class="token comment">// undefined</span>
a <span class="token operator">=</span> <span class="token keyword">null</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span> <span class="token comment">// null</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br></div></div><ol start="2"><li><strong>什么时候给变量赋值为null呢?</strong></li></ol> <ul><li>初始赋值, 表明将要赋值为对象,可以用做约定俗成的占位符</li> <li>结束前, 让对象成为垃圾对象(被垃圾回收器回收)</li> <li>代码示例</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 起始,可以用做约定俗成的占位符</span>
<span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token keyword">null</span>  <span class="token comment">// 初始赋值为null, 表明将要赋值为对象</span>

<span class="token comment">// 确定对象就赋值</span>
b <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token string">'atguigu'</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">]</span>

<span class="token comment">// 最后在不使用的时候，将其引用置空，就可以释放b这个对象占用的内存</span>
<span class="token comment">// 当没有引用指向它的对象称为垃圾对象</span>
b <span class="token operator">=</span> <span class="token keyword">null</span> <span class="token comment">// 让b指向的对象成为垃圾对象(被垃圾回收器回收)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br></div></div><ol start="3"><li><strong>严格区别变量类型与数据类型?</strong></li></ol> <ul><li>数据的类型</li> <li>基本类型</li> <li>对象类型</li> <li>变量的类型(变量内存值的类型)</li> <li>基本类型: 保存就是基本类型的数据</li> <li>引用类型: 保存的是地址值(对象类型)</li></ul> <p><strong>Ⅴ-补充知识点</strong></p> <p><strong>符串对比<code>&gt;</code>、<code>&lt;</code>以及<code>charCodeAt()</code>方法</strong></p> <ul><li>Javascript字符串在进行大于(小于)比较时，会根据<strong>第一个不同的字符的ascii值码</strong>进行比较</li> <li>当数字(number)与字符串(string)进行比较大小时，会**强制的将数字(number)转换成字符串(string)**然后再进行比较</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token punctuation">(</span><span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'13'</span> <span class="token operator">&gt;</span> <span class="token string">'3'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>		<span class="token comment">// false</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token number">5</span> <span class="token operator">&gt;</span> <span class="token string">'6'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>				<span class="token comment">// false</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'d'</span> <span class="token operator">&gt;</span> <span class="token string">'ABDC'</span><span class="token punctuation">)</span> 	<span class="token comment">// true</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token number">19</span> <span class="token operator">&gt;</span> <span class="token string">'ssf'</span><span class="token punctuation">)</span>			<span class="token comment">// false</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'A'</span> <span class="token operator">&gt;</span> <span class="token string">'abcdef'</span><span class="token punctuation">)</span>	<span class="token comment">// false</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><ul><li>手动转换为ascii后相减,用正负数表示大小</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>sorter <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">(</span><span class="token parameter"><span class="token literal-property property">a</span><span class="token operator">:</span>string<span class="token punctuation">,</span> <span class="token literal-property property">b</span><span class="token operator">:</span>string</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> a<span class="token punctuation">.</span><span class="token function">charCodeAt</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">-</span> b<span class="token punctuation">.</span><span class="token function">charCodeAt</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">}</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br></div></div><h3 id="_1-2-数据-变量-内存的理解"><a href="#_1-2-数据-变量-内存的理解" class="header-anchor">#</a> 1.2 数据,变量, 内存的理解</h3> <p><strong>Ⅰ-什么是数据</strong></p> <ol><li>存储在内存中代表特定信息的'东西'，本质上是二进制0101...</li> <li>数据的特点：可传递，可运算 --&gt;let a=0;b=a 🔜体现可传递</li> <li>一切皆数据</li> <li>内存中所有操作的目标：数据
<ul><li>算术运算</li> <li>逻辑运算</li> <li>赋值</li> <li>运行函数</li></ul></li></ol> <p><strong>Ⅱ-什么是内存</strong></p> <ol><li>内存条通电后产生的可储存数据的空间(临时的)</li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211161631827.png" alt="ROM3"></p> <ol start="2"><li><p>内存产生和死亡：内存条(电路版)&gt;==通电==&gt;产生内存空间 == &gt;存储数据 == &gt;处理数据== &gt;断电==&gt;内存空间和数据都消失</p></li> <li><p>一块小内存的2个数据</p></li></ol> <ul><li>内部存储的数据</li> <li>地址值</li></ul> <ol start="4"><li>内存分类
<ul><li>堆：全局变量/局部变量</li> <li>栈：对象</li></ul></li></ol> <img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211161635615.png" alt="rom4" style="zoom:80%;"> <p><strong>Ⅳ-内存,数据, 变量三者之间的关系</strong></p> <ul><li>内存用来存储数据的空间</li> <li>变量是内存的标识</li></ul> <p><strong>Ⅴ-相关问题引出</strong></p> <p><strong>① 关于赋值和内存的问题</strong></p> <p>let a = xxx, a内存中到底保存的是什么?</p> <ul><li>xxx是基本数据, 保存的就是这个数据</li> <li>xxx是对象, 保存的是对象的地址值</li> <li>xxx是一个变量, 保存的xxx的内存内容(可能是基本数据, 也可能是地址值)</li></ul> <p><strong>② 关于引用变量赋值问题</strong></p> <ul><li>2个引用变量指向同一个对象, 通过一个变量修改对象内部数据, 另一个变量看到的是修改之后的数据</li> <li>2个引用变量指向同一个对象, 让其中一个引用变量指向另一个对象, 另一引用变量依然指向前一个对象</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">let</span> a <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token literal-property property">age</span><span class="token operator">:</span> <span class="token number">12</span><span class="token punctuation">}</span>

<span class="token comment">// 此时是将a指向的地址值赋值给B,所以B此时也指向{age:12}这个内存</span>
<span class="token keyword">let</span> b <span class="token operator">=</span> a

<span class="token comment">// 此时重新创建了一个内存并让a指向它，所以此处a指向的是{name:'hong'}，而b指向仍是{age:12}</span>
a <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token literal-property property">name</span><span class="token operator">:</span> <span class="token string">'hong'</span><span class="token punctuation">}</span>

<span class="token comment">// 此时a与b指向的内存已经不一样了,所以修改互不影响</span>
b<span class="token punctuation">.</span>age <span class="token operator">=</span> <span class="token number">14</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b<span class="token punctuation">.</span>age<span class="token punctuation">,</span> a<span class="token punctuation">.</span>name<span class="token punctuation">,</span> a<span class="token punctuation">.</span>age<span class="token punctuation">)</span> <span class="token comment">// 14 hong undefined</span>

<span class="token comment">// 2个引用变量指向同一个对象, 让一个指向其他个对象, 另一依然指向前一个对象，a仍是{name: 'hong'}</span>
<span class="token keyword">const</span> <span class="token function-variable function">fn2</span><span class="token operator">=</span><span class="token punctuation">(</span><span class="token parameter">obj</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token literal-property property">age</span><span class="token operator">:</span> <span class="token number">15</span><span class="token punctuation">}</span>
<span class="token function">fn2</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">.</span>age<span class="token punctuation">)</span> <span class="token comment">// undefined</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p><strong>③ 在js调用函数时传递变量参数时, 是值传递还是引用传递</strong></p> <ul><li>都是值传递</li> <li>所以实际上传进function中的参数也是拿着其存着的地址值找内存</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 传进来的obj存储的是a中存的地址值,所以obj==a(因为他们地址值一致,指向一致)</span>
<span class="token comment">// 2个引用变量指向同一个对象, 通过一个变量修改对象内部数据, </span>
<span class="token comment">// 另一个变量看到的是修改之后的数据，所以被进行了修改</span>
<span class="token keyword">let</span> a <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token literal-property property">name</span><span class="token operator">:</span> <span class="token string">'hong'</span><span class="token punctuation">}</span>
<span class="token keyword">const</span> <span class="token function-variable function">fn2</span><span class="token operator">=</span><span class="token punctuation">(</span><span class="token parameter">obj</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> obj<span class="token punctuation">.</span>age<span class="token operator">=</span> <span class="token number">15</span>
<span class="token function">fn2</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">.</span>age<span class="token punctuation">)</span> <span class="token comment">//15 </span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><p><strong>④ JS引擎如何管理内存?</strong></p> <ol><li>内存生命周期
<ul><li>分配小内存空间, 得到它的使用权</li> <li>存储数据, 可以反复进行操作</li> <li>释放小内存空间</li></ul></li> <li>释放内存
<ul><li>局部变量: 函数执行完自动释放</li> <li>对象: 成为垃圾对象==&gt;垃圾回收器回收</li></ul></li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">3</span>
<span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token literal-property property">name</span><span class="token operator">:</span><span class="token string">&quot;hong&quot;</span><span class="token punctuation">}</span>
obj <span class="token operator">=</span> <span class="token keyword">undefined</span> <span class="token operator">||</span><span class="token keyword">null</span>  <span class="token comment">//此时,obj没有被释放,但是之前声明的`{name:&quot;hong&quot;}`由于没有人指向它,会在后面你某个时刻被垃圾回收器回收</span>
<span class="token keyword">function</span> <span class="token function">fn</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">}</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// b是自动释放, b所指向的对象是在后面的某个时刻由垃圾回收器回收</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br></div></div><h3 id="_1-3-对象"><a href="#_1-3-对象" class="header-anchor">#</a> 1.3 对象</h3> <p><strong>Ⅰ-对象的概念</strong></p> <p><strong>① 什么是对象?</strong></p> <ul><li>多个数据的封装体</li> <li>用来保存多个数据的容器</li> <li>一个对象代表现实中的一个事物</li></ul> <p><strong>② 为什么要用对象?</strong></p> <ul><li>统一管理多个数据</li></ul> <p><strong>③ 对象的组成</strong></p> <ul><li>属性: 属性名(字符串)和属性值(任意)组成</li> <li>方法: 一种特别的属性(属性值是函数)</li></ul> <p><strong>Ⅱ-如何访问对象内部数据?</strong></p> <ul><li><p><font color="#d00"><code>.属性名</code></font>编码简单，有时不能用</p></li> <li><p><font color="#d00"><code>['属性名']</code></font>编码麻烦，能通用</p></li></ul> <p><strong>Ⅲ-什么时候必须使用['属性名']的方式?</strong></p> <ol><li>属性名包含特殊字符: <code>-</code> <code>空格</code></li> <li>属性名不确定</li></ol> <div class="language- line-numbers-mode"><pre class="language-text"><code>var p = {}
//1. 给p对象添加一个属性: content type: text/json
// p.content-type = 'text/json' //不能用
p['content-type'] = 'text/json'
console.log(p['content-type'])

//2. 属性名不确定
var propName = 'myAge'
var value = 18
// p.propName = value //不能用
p[propName] = value
console.log(p[propName])
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><h3 id="_1-4-函数"><a href="#_1-4-函数" class="header-anchor">#</a> 1.4 函数</h3> <p><strong>Ⅰ 函数的概念</strong></p> <ol><li><strong>什么是函数</strong></li></ol> <ul><li>实现特定功能的 n 条语句的封装体</li> <li>只有函数是可以执行的，其它类型的数据不能执行</li> <li>==<strong>凡是通过 new Function() 创建的对象都是函数对象（本质）</strong>==</li></ul> <ol start="2"><li><strong>为什么要用函数?</strong></li></ol> <ul><li>提高代码复用</li> <li>便于阅读交流</li></ul> <ol start="3"><li><strong>定义函数</strong> <ul><li>函数声明</li> <li>表达式</li></ul></li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 函数声明</span>
<span class="token keyword">function</span> <span class="token function">fn1</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> 
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn1()'</span><span class="token punctuation">)</span> 
<span class="token punctuation">}</span>
<span class="token keyword">const</span> <span class="token function-variable function">fn2</span> <span class="token operator">=</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn2()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token keyword">const</span> <span class="token function-variable function">fn2</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn2()'</span><span class="token punctuation">)</span>  	<span class="token comment">// 表达式</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br></div></div><p><strong>Ⅱ 调用(执行)函数</strong></p> <ol><li><code>test()</code>			直接调用</li> <li><code>obj.test()</code>			通过对象调用</li> <li><code>new test()</code>			new 调用</li> <li><font color="#d00"><code>test.call/apply(obj)</code>	临时让 test 成为 obj 的方法进行调用</font></li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211161656799.png" alt="function3"></p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
<span class="token comment">//此处不能使用箭头函数,因为箭头函数会改变this指向</span>
<span class="token keyword">function</span> <span class="token function">test2</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>xxx <span class="token operator">=</span> <span class="token string">'hongjilin'</span>
<span class="token punctuation">}</span>

<span class="token comment">// obj.test2()  不能直接, 根本就没有</span>
<span class="token function">test2</span><span class="token punctuation">.</span><span class="token function">call</span><span class="token punctuation">(</span>obj<span class="token punctuation">)</span>  <span class="token comment">// 可以让一个函数成为指定任意对象的方法进行调用</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>obj<span class="token punctuation">.</span>xxx<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br></div></div><p><strong>Ⅲ 回调函数</strong></p> <ol><li><strong>回调函数</strong></li></ol> <p>​		a. 你定义的
​		b. 你没有调
​		c. 但最终它执行了（在某个时刻或某个条件下）</p> <ol start="2"><li><strong>常见的回调函数</strong></li></ol> <ul><li>dom事件回调函数 ==&gt; 发生事件的dom元素</li> <li>定时器回调函数 ===&gt; window</li> <li>ajax请求回调函数</li> <li>生命周期回调函数</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// dom事件回调函数</span>
document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'btn'</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token function">alert</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>innerHTML<span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token comment">// 定时器回调函数</span>
<span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'到点了'</span><span class="token operator">+</span><span class="token keyword">this</span><span class="token punctuation">)</span> 
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">2000</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br></div></div><p><strong>Ⅳ IIFE (自调用函数 Immediately-Invoked Function Expression)</strong></p> <ul><li>隐藏实现</li> <li>不会污染外部（一般指全局）命名空间</li> <li>用它来编码 js 模块</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">// 匿名函数自调用</span>
<span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> 
  <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">3</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a <span class="token operator">+</span> <span class="token number">3</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>	<span class="token comment">// a is not defined</span>

<span class="token comment">// 此处要加一个分号</span>
<span class="token comment">// 因为自调用函数外部有一个()包裹，可能与前方以()结尾的代码合在一起认为是函数调用</span>
<span class="token comment">// console.log(a)(IIFE)</span>
<span class="token punctuation">;</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>	<span class="token comment">// 不会污染外部(全局)命名空间--&gt;举例</span>
  <span class="token keyword">let</span> a <span class="token operator">=</span> <span class="token number">1</span><span class="token punctuation">;</span>
  <span class="token keyword">function</span> <span class="token function">test</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>	<span class="token comment">//声明一个局部函数test</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token operator">++</span>a<span class="token punctuation">)</span> 
  <span class="token punctuation">}</span> 
  window<span class="token punctuation">.</span><span class="token function-variable function">$</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>	<span class="token comment">// 向外暴露一个全局函数 1. $是一个函数 2. $执行后返回的是一个对象</span>
    <span class="token keyword">return</span> <span class="token punctuation">{</span>
      <span class="token literal-property property">test</span><span class="token operator">:</span> test
    <span class="token punctuation">}</span> 
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token comment">// test ()	// test is not defined</span>
<span class="token function">$</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">test</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
Ⅴ 函数中的 <span class="token keyword">this</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br></div></div><p><strong>Ⅴ 函数中的 this</strong></p> <ol><li><strong>this</strong></li></ol> <ul><li>任何函数本质上都是通过某个对象来调用的，如果没有直接指定就是window</li> <li>所有函数内部都有一个变量 this</li> <li>它的值是<font color="#d00">调用函数的当前对象 </font></li></ul> <ol start="2"><li><strong>如何确定this的值？</strong></li></ol> <ul><li><code>test()</code>		window</li> <li><code>p.test()</code>		p</li> <li><code>new test()</code>	新创建的对象</li> <li><code>p.call(obj)</code>	obj</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">color</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">)</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>color <span class="token operator">=</span> color<span class="token punctuation">;</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function-variable function">getColor</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">)</span>
    <span class="token keyword">return</span> <span class="token keyword">this</span><span class="token punctuation">.</span>color<span class="token punctuation">;</span>
  <span class="token punctuation">}</span><span class="token punctuation">;</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function-variable function">setColor</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">color</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">)</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>color <span class="token operator">=</span> color<span class="token punctuation">;</span>
  <span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>

<span class="token keyword">const</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token function">Person</span><span class="token punctuation">(</span><span class="token string">&quot;red&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// this是谁? window</span>

<span class="token keyword">const</span> p <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">&quot;yello&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// this是谁? p</span>
p<span class="token punctuation">.</span><span class="token function">getColor</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">//this是谁? p</span>

<span class="token comment">// 调用call会改变this指向--&gt;让我的p函数成为`obj`的临时方法进行调用</span>
p<span class="token punctuation">.</span><span class="token function">setColor</span><span class="token punctuation">.</span><span class="token function">call</span><span class="token punctuation">(</span>obj<span class="token punctuation">,</span> <span class="token string">&quot;black&quot;</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// this是谁? obj</span>

<span class="token keyword">const</span> test <span class="token operator">=</span> p<span class="token punctuation">.</span>setColor<span class="token punctuation">;</span>
<span class="token function">test</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// this是谁? window  --&gt;因为直接调用了</span>

<span class="token keyword">function</span> <span class="token function">fun1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">function</span> <span class="token function">fun2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>  
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span>
  <span class="token function">fun2</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>	<span class="token comment">// this是谁? window</span>
<span class="token punctuation">}</span>
<span class="token function">fun1</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>	<span class="token comment">// 调用fun1</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br><span class="line-number">29</span><br><span class="line-number">30</span><br><span class="line-number">31</span><br><span class="line-number">32</span><br></div></div><h3 id="_1-5-关于语句分号"><a href="#_1-5-关于语句分号" class="header-anchor">#</a> 1.5 关于语句分号</h3> <ol><li><p>js 一条语句的后面可以不加分号</p></li> <li><p>是否加分号是编码风格问题，没有应该不应该，只有你自己喜欢不喜欢</p></li> <li><p>在下面 2 种情况下不加分号会有问题</p> <ul><li><p>小括号开头的前一条语句</p></li> <li><p>中方括号开头的前一条语句</p></li></ul></li> <li><p>解决办法：在行首加分号</p></li> <li><p>强有力的例子vue.js库</p></li> <li><p>知乎热议 https://www.zhihu.com/question/20298345</p></li></ol> <h2 id="二、-函数高级"><a href="#二、-函数高级" class="header-anchor">#</a> 二、 函数高级</h2> <h2 id="_2-1-原型与原型链"><a href="#_2-1-原型与原型链" class="header-anchor">#</a> 2.1 原型与原型链</h2> <p><strong>Ⅰ 原型 prototype</strong></p> <ol><li>函数的<font color="#d00">prototype</font>属性
<ul><li>每个<font color="#d00">函数</font>都有一个<font color="#d00"> prototype</font> 属性，它默认指向一个 Object 空对象（即称为 原型对象）</li> <li>原型对象中有一个属性 <font color="#d00">constructor</font>，它指向函数对象</li></ul></li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180921773.png" alt="prototype"></p> <ol start="2"><li>给原型对象添加属性（一般都是方法）
<ul><li>作用: 函数的所有实例对象自动拥有原型中的属性（方法）</li></ul></li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 每个函数都有一个 prototype 属性, 它默认指向一个 Object 空对象(即称为: 原型对象)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Date</span><span class="token punctuation">.</span>prototype<span class="token punctuation">,</span> <span class="token keyword">typeof</span> <span class="token class-name">Date</span><span class="token punctuation">.</span>prototype<span class="token punctuation">)</span>

<span class="token keyword">function</span> <span class="token function">Fun</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
<span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Fun</span><span class="token punctuation">.</span>prototype<span class="token punctuation">)</span>  <span class="token comment">// 默认指向一个 Object 空对象(没有自己的属性)</span>

<span class="token comment">// 原型对象中有一个属性constructor, 它指向函数对象</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Date</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>constructor <span class="token operator">===</span> Date<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Fun</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>constructor <span class="token operator">===</span> Fun<span class="token punctuation">)</span>

<span class="token comment">// 给原型对象添加属性、方法(一般是方法) ===&gt; 实例对象可以访问</span>
<span class="token class-name">Fun</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">test</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> 
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'test()'</span><span class="token punctuation">)</span> 
<span class="token punctuation">}</span>

<span class="token keyword">var</span> fun <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Fun</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
fun<span class="token punctuation">.</span><span class="token function">test</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br></div></div><p><strong>Ⅱ 显式原型与隐式原型</strong></p> <ol><li>每个函数 function 都有一个<code>prototype</code>，即==显式原型==属性</li> <li>每个实例对象都有一个<code>__ proto __</code>，可称为==隐式原型==属性</li> <li>对象的==隐式原型的值为其对应构造函数的显式原型的值==</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">//定义构造函数</span>
<span class="token keyword">function</span> <span class="token function">Fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 内部默认执行语句: this.prototype = {}</span>
<span class="token punctuation">}</span>
<span class="token comment">// 1. 每个函数function都有一个prototype，即显式原型属性, 默认指向一个空的Object对象</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Fn</span><span class="token punctuation">.</span>prototype<span class="token punctuation">)</span>


<span class="token comment">// 创建实例对象</span>
<span class="token keyword">var</span> fn <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>  <span class="token comment">// 内部默认执行语句: this.__proto__ = Fn.prototype</span>
<span class="token comment">// 2. 每个实例对象都有一个__proto__，可称为隐式原型</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>fn<span class="token punctuation">.</span>__proto__<span class="token punctuation">)</span>

<span class="token comment">// 3. 对象的隐式原型的值为其对应构造函数的显式原型的值</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Fn</span><span class="token punctuation">.</span>prototype <span class="token operator">===</span> fn<span class="token punctuation">.</span>__proto__<span class="token punctuation">)</span> <span class="token comment">// true</span>

<span class="token comment">// 给原型添加方法</span>
<span class="token class-name">Fn</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">test</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'test()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token comment">// 通过实例调用原型的方法</span>
fn<span class="token punctuation">.</span><span class="token function">test</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br></div></div><ol start="4"><li>内存结构</li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180927790.png" alt="prototype2"></p> <ol start="5"><li>总结</li></ol> <ul><li><p>函数的 <strong>prototype</strong> 属性：在定义函数时自动添加的，默认值是一个空 Object 实例对象（<strong>Object 函数</strong>除外，因为其 <strong>__ proto __</strong> 属性为 null）</p></li> <li><p>对象的 <strong>__ proto __</strong> 属性：创建对象时自动添加的，默认值为构造函数的 prototype 属性值，Function函数</p></li> <li><p>程序员==可以直接操作显式原型，但不能直接操作隐式原型==（ES6之前）</p></li></ul> <p><strong>Ⅲ 原型链</strong></p> <ol><li>原型链</li></ol> <ul><li>访问一个对象的属性时，</li> <li>先在自身属性中查找，找到返回</li> <li>如果没有, 再沿着<code>__ proto __</code>这条链向上查找，找到返回</li> <li>如果最终没找到，返回 undefined</li></ul> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180929453.png" alt="prototype3"></p> <ul><li>别名：隐式原型链</li> <li>作用：查找对象的属性（方法）</li></ul> <ol start="2"><li><strong>构造函数/原型/实例对象的关系（图解）</strong></li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> o1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Object</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token keyword">var</span> o2 <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">;</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180930622.png" alt="prototype4"></p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">Foo</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>  <span class="token punctuation">}</span> 等价于 <span class="token keyword">let</span> Foo <span class="token operator">=</span> <span class="token function">Function</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
<span class="token comment">// 系统创建</span>
Function <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Function</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br></div></div><p>==<strong>所有函数的<code>__ proto __</code>都是一样的</strong>==</p> <ul><li>函数现实原型默认值是一个空 Object 实例对象（<strong>Object 函数</strong>除外，因为其**__ proto <em>**</em> 属性为 null）</li> <li>所有函数都是 <strong>Function 函数</strong>的实例，包括 Function 本身</li> <li><strong>Object</strong> 的原型对象是原型链的尽头 <code>Object.prototype.__proto__</code>为 null</li></ul> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180932122.png" alt="PROTOTYPE5"></p> <ol start="3"><li>属性问题
<ul><li><strong><font color="#d00">读取</font>对象的属性值时：会自动到<font color="#d00">原型链</font>中查找</strong></li> <li><strong><font color="#d00">设置</font>对象的属性值时：不会查找原型链，如果当前对象中没有此属性，直接添加此属性并设置其值</strong></li> <li>方法一般定义在原型中，属性一般通过构造函数定义在对象本身上</li></ul></li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token keyword">function</span> <span class="token function">Fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token punctuation">}</span>
<span class="token class-name">Fn</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>a <span class="token operator">=</span> <span class="token string">'xxx'</span>

<span class="token keyword">var</span> fn1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token keyword">var</span> fn2 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
fn2<span class="token punctuation">.</span>a <span class="token operator">=</span> <span class="token string">'yyy'</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>fn1<span class="token punctuation">.</span>a<span class="token punctuation">,</span> fn2<span class="token punctuation">.</span>a<span class="token punctuation">,</span> fn2<span class="token punctuation">)</span> <span class="token comment">//xxx yyy  Fn{a: &quot;yyy&quot;}</span>

<span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>age <span class="token operator">=</span> age
<span class="token punctuation">}</span>
<span class="token class-name">Person</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">setName</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
<span class="token punctuation">}</span>

<span class="token keyword">var</span> p1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span>
p1<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'Bob'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1<span class="token punctuation">)</span>  <span class="token comment">//Person {name: &quot;Bob&quot;, age: 12}</span>

<span class="token keyword">var</span> p2 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'Jack'</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span>
p2<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'Cat'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p2<span class="token punctuation">)</span> <span class="token comment">//Person {name: &quot;Cat&quot;, age: 12}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1<span class="token punctuation">.</span>__proto__<span class="token operator">===</span>p2<span class="token punctuation">.</span>__proto__<span class="token punctuation">)</span> <span class="token comment">// true   --&gt;所以方法一般定义在原型中</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br></div></div><p><strong>Ⅳ instanceof</strong></p> <ol><li><p>instanceof是如何判断的?</p> <ul><li>表达式 <code>A instanceof B</code></li> <li><strong>如果B函数的显式原型对象在A对象的原型链上, 返回 true, 否则返回 false</strong></li></ul></li> <li><p>Function是通过new自己产生的实例</p></li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 案例1</span>
<span class="token keyword">function</span> <span class="token function">Foo</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>  <span class="token punctuation">}</span>
<span class="token keyword">var</span> f1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Foo</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>f1 <span class="token keyword">instanceof</span> <span class="token class-name">Foo</span><span class="token punctuation">)</span>		<span class="token comment">// true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>f1 <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">)</span> <span class="token comment">// true</span>

<span class="token comment">// 案例2</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>Object <span class="token keyword">instanceof</span> <span class="token class-name">Function</span><span class="token punctuation">)</span>		<span class="token comment">// true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>Object <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">)</span>			<span class="token comment">// true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>Function <span class="token keyword">instanceof</span> <span class="token class-name">Function</span><span class="token punctuation">)</span> <span class="token comment">// true</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>Function <span class="token keyword">instanceof</span> <span class="token class-name">Object</span><span class="token punctuation">)</span>		<span class="token comment">// true</span>
<span class="token keyword">function</span> <span class="token function">Foo</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>Object <span class="token keyword">instanceof</span>  <span class="token class-name">Foo</span><span class="token punctuation">)</span> <span class="token comment">// false</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br></div></div><p><strong>Ⅴ 相关面试题</strong></p> <p>测试题1</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token constant">A</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
<span class="token class-name">A</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>n <span class="token operator">=</span> <span class="token number">1</span>
<span class="token keyword">let</span> b <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">A</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token class-name">A</span><span class="token punctuation">.</span>prototype <span class="token operator">=</span> <span class="token punctuation">{</span> <span class="token literal-property property">n</span><span class="token operator">:</span> <span class="token number">2</span><span class="token punctuation">,</span> <span class="token literal-property property">m</span><span class="token operator">:</span> <span class="token number">3</span><span class="token punctuation">}</span>	<span class="token comment">// 这里是改了A.prototype的引用</span>
<span class="token keyword">let</span> c <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">A</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b<span class="token punctuation">.</span>n<span class="token punctuation">,</span> b<span class="token punctuation">.</span>m<span class="token punctuation">,</span> c<span class="token punctuation">.</span>n<span class="token punctuation">,</span> c<span class="token punctuation">.</span>m<span class="token punctuation">)</span> <span class="token comment">// 1 undefined 2 3</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br></div></div><p>测试题2 原理看 构造函数/原型/实例对象的关系(图解)</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token constant">F</span> <span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span><span class="token punctuation">}</span>
<span class="token class-name">Object</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">a</span> <span class="token operator">=</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'a()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token class-name">Function</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">b</span> <span class="token operator">=</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'b()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token keyword">let</span> f <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">F</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
f<span class="token punctuation">.</span><span class="token function">a</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">//a()</span>
f<span class="token punctuation">.</span><span class="token function">b</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">//f.b is not a function --&gt;找不到</span>
<span class="token constant">F</span><span class="token punctuation">.</span><span class="token function">a</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">//a()</span>
<span class="token constant">F</span><span class="token punctuation">.</span><span class="token function">b</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">//b()</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>f<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Object</span><span class="token punctuation">.</span>prototype<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token class-name">Function</span><span class="token punctuation">.</span>prototype<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180935729.png" alt="test1"></p> <h3 id="_2-2-执行上下文与执行上下文栈-类似java的栈-上下文就是栈帧"><a href="#_2-2-执行上下文与执行上下文栈-类似java的栈-上下文就是栈帧" class="header-anchor">#</a> 2.2 执行上下文与执行上下文栈（类似Java的栈，上下文就是栈帧）</h3> <p>启动程序时，从全局执行上下文中开始。一些变量是在全局执行上下文中声明的，称之为全局变量
<strong>当程序调用一个函数时</strong></p> <ul><li>JavaScript 创建一个<strong>本地执行上下文</strong></li> <li>本地执行上下文将有它自己的一组变量，作为本地变量</li> <li>本地执行上下文被推到到执行栈中</li></ul> <p><strong>当一个函数结束时</strong></p> <ul><li>本地执行上下文从执行栈中弹出</li> <li>函数将返回值返回调用上下文。调用上下文是调用这个本地的执行上下文，它可以是全局执行上下文，也可以是另外一个本地的执行上下文。这取决于调用执行上下文来处理此时的返回值，返回的值可以是一个对象、一个数组、一个函数、一个布尔值等等，如果函数没有 return 语句，则返回 undefined</li> <li>本地执行上下文被销毁，本地执行上下文中声明的所有变量都将被删除</li></ul> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180936541.png" alt="执行上下文"></p> <p><strong>Ⅰ 变量提升与函数提升</strong></p> <ol><li>变量声明提升
<ul><li>通过var定义(声明)的变量，在定义语句之前就可以访问到</li> <li>值: undefined</li></ul></li> <li>函数声明提升
<ul><li>通过 function 声明的函数，在之前就可以直接调用</li> <li>值: 函数定义(对象)</li></ul></li></ol> <p>引出一个问题：变量提升和函数提升是如何产生的?</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">1</span>
<span class="token keyword">function</span> <span class="token function">fn</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
  <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">2</span>	<span class="token comment">// 变量提升</span>
<span class="token punctuation">}</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>  <span class="token comment">// undefined</span>
<span class="token string">'--------------------------------------------'</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b<span class="token punctuation">)</span> <span class="token comment">//undefined  变量提升</span>
<span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span>	<span class="token comment">// 可调用，函数提升</span>
<span class="token comment">// fn3()不能变量提升</span>
<span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token number">3</span>
<span class="token keyword">function</span> <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn2()'</span><span class="token punctuation">)</span> <span class="token punctuation">}</span>
<span class="token keyword">var</span> <span class="token function-variable function">fn3</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn3()'</span><span class="token punctuation">)</span> <span class="token punctuation">}</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br></div></div><p><strong>Ⅱ 执行上下文</strong></p> <p>代码分类(位置)</p> <ul><li>全局代码</li> <li>函数（局部）代码</li></ul> <p>全局执行上下文</p> <ol><li><p>1在执行全局代码前将 window 确定为全局执行上下文</p></li> <li><p>对全局数据进行预处理</p> <ul><li>var定义的全局变量==&gt;undefined，添加为 window 的属性</li> <li>function声明的全局函数==&gt;赋值，添加为 window 的方法</li> <li>this==&gt;赋值 window</li></ul></li> <li><p>开始执行全局代码</p></li></ol> <p>函数执行上下文</p> <ol><li><p>在调用函数前，创建对应的函数执行上下文对象（虚拟的，存在于栈中）</p></li> <li><p>对局部数据进行预处理</p> <ul><li><p>形参变量赋值实参，添加为执行上下文的属性</p></li> <li><p><strong>arguments</strong> 赋值实参列表，添加为执行上下文的属性</p></li> <li><p>var 定义的局部变量 undefined，添加为执行上下文的属性</p></li> <li><p>function声明的函数赋值 fun，添加为执行上下文的方法</p></li> <li><p>this赋值(调用函数的对象）</p></li></ul></li> <li><p>开始执行函数体代码</p></li></ol> <p><strong>Ⅲ 执行上下文栈</strong></p> <ol><li>在全局代码执行前，JS 引擎就会创建一个栈来存储管理所有的执行上下文对象</li> <li>在全局执行上下文 window 确定后，将其添加到栈中，所以栈底百分百是 window</li> <li>在函数执行上下文创建后，将其添加到栈中(压栈)</li> <li>在当前函数执行完后，将栈顶的对象移除(出栈)</li> <li>当所有的代码执行完后, 栈中只剩下window</li> <li>上下文栈数==函数调用数+1</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">//1. 进入全局执行上下文</span>
<span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">10</span>
<span class="token keyword">var</span> <span class="token function-variable function">bar</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">x</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token number">5</span>
  <span class="token function">foo</span><span class="token punctuation">(</span>x <span class="token operator">+</span> b<span class="token punctuation">)</span>   <span class="token comment">//3. 进入foo执行上下文</span>
<span class="token punctuation">}</span>
<span class="token keyword">var</span> <span class="token function-variable function">foo</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">y</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token number">5</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a <span class="token operator">+</span> c <span class="token operator">+</span> y<span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token function">bar</span><span class="token punctuation">(</span><span class="token number">10</span><span class="token punctuation">)</span> <span class="token comment">//2. 进入bar函数执行上下文</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180943108.png" alt="上下文"></p> <p><strong>Ⅳ 相关面试题</strong></p> <p>函数提升优先级高于变量提升,且不会被变量声明覆盖,但是会被变量赋值覆盖</p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 测试题1:  先执行变量提升, 再执行函数提升</span>
<span class="token keyword">function</span> <span class="token function">a</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
<span class="token keyword">var</span> a
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">typeof</span> a<span class="token punctuation">)</span> <span class="token comment">// 'function'</span>

<span class="token comment">// 测试题2:</span>
<span class="token keyword">if</span> <span class="token punctuation">(</span><span class="token operator">!</span><span class="token punctuation">(</span>b <span class="token keyword">in</span> window<span class="token punctuation">)</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token number">1</span>
<span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b<span class="token punctuation">)</span> <span class="token comment">// undefined</span>

<span class="token comment">// 测试题3:</span>
<span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token number">1</span>
<span class="token keyword">function</span> <span class="token function">c</span><span class="token punctuation">(</span><span class="token parameter">c</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>c<span class="token punctuation">)</span>
  <span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token number">3</span> <span class="token comment">//与此行无关</span>
<span class="token punctuation">}</span>
<span class="token function">c</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span> <span class="token comment">// 报错  c is not a function</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br></div></div><h3 id="_2-3-作用域与作用域链-就是变量起作用的范围-与java一致"><a href="#_2-3-作用域与作用域链-就是变量起作用的范围-与java一致" class="header-anchor">#</a> 2.3 作用域与作用域链（就是变量起作用的范围，与Java一致）</h3> <p><strong>Ⅰ 作用域</strong></p> <p><strong>理解</strong></p> <ul><li>就是一块&quot;地盘&quot;，一段代码段所在的区域</li> <li>它是静态的（相对于上下文对象），在编写代码时就确定了</li></ul> <p><strong>分类</strong></p> <ul><li>全局作用域</li> <li>函数作用域</li> <li>ES6 新增块作用域</li></ul> <p><strong>作用</strong></p> <ul><li>隔离变量，不同作用域下同名变量不会有冲突</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">//没块作用域</span>
<span class="token keyword">if</span><span class="token punctuation">(</span><span class="token boolean">true</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token number">3</span> <span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>c<span class="token punctuation">)</span>

<span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">10</span><span class="token punctuation">,</span>
    b <span class="token operator">=</span> <span class="token number">20</span>
<span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token parameter">x</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">100</span><span class="token punctuation">,</span> c <span class="token operator">=</span> <span class="token number">300</span><span class="token punctuation">;</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn()'</span><span class="token punctuation">,</span> a<span class="token punctuation">,</span> b<span class="token punctuation">,</span> c<span class="token punctuation">,</span> x<span class="token punctuation">)</span> <span class="token comment">//100 20 300 10</span>
  <span class="token keyword">function</span> <span class="token function">bar</span><span class="token punctuation">(</span><span class="token parameter">x</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">1000</span><span class="token punctuation">,</span> d <span class="token operator">=</span> <span class="token number">400</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'bar()'</span><span class="token punctuation">,</span> a<span class="token punctuation">,</span> b<span class="token punctuation">,</span> c<span class="token punctuation">,</span> d<span class="token punctuation">,</span> x<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token function">bar</span><span class="token punctuation">(</span><span class="token number">100</span><span class="token punctuation">)</span>	<span class="token comment">// 1000 20 300 400 100</span>
  <span class="token function">bar</span><span class="token punctuation">(</span><span class="token number">200</span><span class="token punctuation">)</span>	<span class="token comment">// 1000 20 300 400 200</span>
<span class="token punctuation">}</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token number">10</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br></div></div><p><strong>Ⅱ 作用域与执行上下文的区别与联系</strong></p> <ol><li>区别1</li></ol> <ul><li>全局作用域之外，每个函数都会创建自己的作用域，作用域在函数定义时就已经确定，而不是在函数调用时</li> <li>全局执行上下文环境是在全局作用域确定之后，js代码马上执行之前创建</li> <li>函数执行上下文是在调用函数时，函数体代码执行之前创建</li></ul> <ol start="2"><li>区别2</li></ol> <ul><li>作用域是静态的，只要函数定义好了就一直存在，且不会再变化</li> <li>执行上下文是动态的，调用函数时创建，函数调用结束时就会自动释放</li></ul> <ol start="3"><li>联系</li></ol> <ul><li><p>执行上下文(对象)是从属于所在的作用域</p></li> <li><p>全局上下文环境 ==&gt; 全局作用域</p></li> <li><p>函数上下文环境 ==&gt; 对应的函数使用域</p></li></ul> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180946602.png" alt="作用域"></p> <p><strong>Ⅲ 作用域链</strong></p> <p><strong>理解</strong></p> <ul><li>多个上下级关系的作用域形成的链，它的方向是从从内到外</li> <li>查找变量时就是沿着作用域链来查找的</li></ul> <p><strong>查找一个变量的查找规则</strong></p> <ol><li>在当前作用域下的执行上下文中查找对应的属性，如果有直接返回, 否则进入2</li> <li>在上一级作用域的执行上下文中查找对应的属性，如果有直接返回, 否则进入3</li> <li>再次执行2的相同操作，直到全局作用域, 如果还找不到就抛出找不到的异常</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">1</span>
 <span class="token keyword">function</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
   <span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token number">2</span>
   <span class="token keyword">function</span> <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
     <span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token number">3</span>
     console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>c<span class="token punctuation">)</span>
     console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>b<span class="token punctuation">)</span>
     console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
     console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>d<span class="token punctuation">)</span>
   <span class="token punctuation">}</span>
   <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
 <span class="token punctuation">}</span>
 <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br></div></div><p><strong>Ⅳ 相关面试题</strong></p> <ol><li>作用域在函数定义时就已经确定了，而不是在函数调用时</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> x <span class="token operator">=</span> <span class="token number">10</span><span class="token punctuation">;</span>
<span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>x<span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token punctuation">}</span>
<span class="token keyword">function</span> <span class="token function">show</span><span class="token punctuation">(</span><span class="token parameter">f</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> x <span class="token operator">=</span> <span class="token number">20</span><span class="token punctuation">;</span>
  <span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span>
<span class="token function">show</span><span class="token punctuation">(</span>fn<span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// 输出10</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180948217.png" alt="test2"></p> <ol start="2"><li>对象变量不能产生局部作用域</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> <span class="token function-variable function">fn</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>fn<span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>

<span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span> 
  <span class="token function-variable function">fn2</span><span class="token operator">:</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>fn2<span class="token punctuation">)</span>	<span class="token comment">//对象变量不能产生局部作用域，所以会找到全局去，导致报错</span>
    <span class="token comment">//console.log(this.fn2)    </span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
obj<span class="token punctuation">.</span><span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><h3 id="_2-4-闭包预备知识点-高阶函数"><a href="#_2-4-闭包预备知识点-高阶函数" class="header-anchor">#</a> 2.4 闭包预备知识点 高阶函数</h3> <p><strong>返回函数的函数[高阶函数]</strong></p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token keyword">let</span> val <span class="token operator">=</span> <span class="token number">7</span>
<span class="token keyword">function</span> <span class="token function">createAdder</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">function</span> <span class="token function">addNumbers</span><span class="token punctuation">(</span><span class="token parameter">a<span class="token punctuation">,</span> b</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">let</span> ret <span class="token operator">=</span> a <span class="token operator">+</span> b
    <span class="token keyword">return</span> ret
  <span class="token punctuation">}</span>
  <span class="token keyword">return</span> addNumbers
<span class="token punctuation">}</span>
<span class="token keyword">let</span> adder <span class="token operator">=</span> <span class="token function">createAdder</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token keyword">let</span> sum <span class="token operator">=</span> <span class="token function">adder</span><span class="token punctuation">(</span>val<span class="token punctuation">,</span> <span class="token number">8</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'example of function returning a function: '</span><span class="token punctuation">,</span> sum<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><p><strong>高阶函数</strong>：就是一个函数就可以接收另一个函数作为参数，或者是返回一个函数--&gt;常见的高阶函数有map、reduce、filter、sort等</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">var</span> <span class="token function-variable function">ADD</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token function">add</span><span class="token punctuation">(</span><span class="token parameter">a</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter">b</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">return</span> a <span class="token operator">+</span> b
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token constant">ADD</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>	<span class="token comment">// 5</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br></div></div><ol><li>map</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// map接受一个函数作为参数，不改变原来的数组，返回一个全新的数组</span>
<span class="token keyword">var</span> arr <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">,</span><span class="token number">2</span><span class="token punctuation">,</span><span class="token number">3</span><span class="token punctuation">,</span><span class="token number">4</span><span class="token punctuation">,</span><span class="token number">5</span><span class="token punctuation">]</span>
<span class="token keyword">var</span> arr1 <span class="token operator">=</span> arr<span class="token punctuation">.</span><span class="token function">map</span><span class="token punctuation">(</span><span class="token parameter">item</span> <span class="token operator">=&gt;</span> item <span class="token operator">=</span> <span class="token number">2</span><span class="token punctuation">)</span>
<span class="token comment">//arr  输出[1,2,3,4,5]</span>
<span class="token comment">//arr1 输出[2,2,2,2,2]</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br></div></div><ol start="2"><li>reduce</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// reduce接受一个函数作为参数，这个函数要有两个形参，代表数组中的前两项，</span>
<span class="token comment">// reduce会将这个函数的结果与数组中的第三项再次组成这个函数的两个形参以此类推进行累积操作</span>
<span class="token keyword">var</span> arr <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">,</span><span class="token number">2</span><span class="token punctuation">,</span><span class="token number">3</span><span class="token punctuation">,</span><span class="token number">4</span><span class="token punctuation">,</span><span class="token number">5</span><span class="token punctuation">]</span>
<span class="token keyword">var</span> arr2 <span class="token operator">=</span> arr<span class="token punctuation">.</span><span class="token function">reduce</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token parameter">a<span class="token punctuation">,</span>b</span><span class="token punctuation">)</span><span class="token operator">=&gt;</span> a<span class="token operator">+</span>b<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>arr2<span class="token punctuation">)</span> <span class="token comment">// 15</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br></div></div><ol start="3"><li>filter</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// filter返回过滤后的数组。filter也接收一个函数作为参数，这个函数将作用于数组中的每个元素，</span>
<span class="token comment">// 根据该函数每次执行后返回的布尔值来保留结果，如果是true就保留，如果是false就过滤掉</span>
<span class="token keyword">var</span> arr <span class="token operator">=</span> <span class="token punctuation">[</span><span class="token number">1</span><span class="token punctuation">,</span><span class="token number">2</span><span class="token punctuation">,</span><span class="token number">3</span><span class="token punctuation">,</span><span class="token number">4</span><span class="token punctuation">,</span><span class="token number">5</span><span class="token punctuation">]</span>
 <span class="token keyword">var</span> arr3 <span class="token operator">=</span> arr<span class="token punctuation">.</span><span class="token function">filter</span><span class="token punctuation">(</span><span class="token parameter">item</span> <span class="token operator">=&gt;</span> item <span class="token operator">%</span> <span class="token number">2</span> <span class="token operator">==</span> <span class="token number">0</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>arr3<span class="token punctuation">)</span>	<span class="token comment">// [2,4]</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br></div></div><h3 id="_2-5-闭包"><a href="#_2-5-闭包" class="header-anchor">#</a> 2.5 闭包</h3> <p><strong>「函数」和「函数内部能访问到的变量」的总和，就是一个闭包（Closure）</strong></p> <ul><li><strong>为什么要函数套函数呢？</strong></li></ul> <p>​		因为需要局部变量，所以才把 变量 放在一个函数里，如果不把 local 放在一个函数里，local 就		是一个全局变量了，达不到使用闭包的目的——隐藏变量。</p> <ul><li><strong>为什么要 return bar 呢？</strong></li></ul> <p>​		因为如果不 return，你就无法使用这个闭包。把 return bar 改成 window.bar = bar 也是一样		的，只要让外面可以访问到这个 bar 函数就行了</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180951713.png" alt="bibao1"></p> <p><strong>Ⅰ 引出闭包概念</strong></p> <ol><li>错误场景</li></ol> <p>​		需求：点击某个按钮，提示“点击的是第n个按钮”</p> <div class="language-html line-numbers-mode"><pre class="language-html"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试1<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试2<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试3<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text/javascript<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
  <span class="token keyword">var</span> btns <span class="token operator">=</span> document<span class="token punctuation">.</span><span class="token function">getElementsByTagName</span><span class="token punctuation">(</span><span class="token string">'button'</span><span class="token punctuation">)</span>
  <span class="token comment">// 注意[btns]不是一个数组,它是一个伪数组</span>
  <span class="token comment">// 每次获取[btns.length]其实都是需要进行计算的(因为它是伪数组)</span>
  <span class="token comment">// 所以为了性能更好，在此处赋值，就只需要计算一次</span>
  <span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">var</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">,</span>length<span class="token operator">=</span>btns<span class="token punctuation">.</span>length<span class="token punctuation">;</span> i <span class="token operator">&lt;</span> length<span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">var</span> btn <span class="token operator">=</span> btns<span class="token punctuation">[</span>i<span class="token punctuation">]</span>
    btn<span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>  <span class="token comment">// 遍历加监听</span>
      <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'第'</span> <span class="token operator">+</span> <span class="token punctuation">(</span>i<span class="token operator">+</span><span class="token number">1</span><span class="token punctuation">)</span> <span class="token operator">+</span> <span class="token string">'个'</span><span class="token punctuation">)</span>     <span class="token comment">// 结果 全是[4]</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>    
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p>此处错误是因为直接修改并使用全局变量[i]，导致for循环结束后，所有点击按钮绑定的弹窗值都是[i+1]
随后调用时，都会找到[i]这个变量，但是此时i==3,所以所有结果都是4</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180952762.png" alt="bibao2"></p> <ol start="2"><li>将变量挂载到自身来解决</li></ol> <p>​		<strong>解决方式:将btn所对应的下标保存在btn上</strong></p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token operator">&lt;</span>button<span class="token operator">&gt;</span>测试<span class="token number">1</span><span class="token operator">&lt;</span><span class="token operator">/</span>button<span class="token operator">&gt;</span>
<span class="token operator">&lt;</span>button<span class="token operator">&gt;</span>测试<span class="token number">2</span><span class="token operator">&lt;</span><span class="token operator">/</span>button<span class="token operator">&gt;</span>
<span class="token operator">&lt;</span>button<span class="token operator">&gt;</span>测试<span class="token number">3</span><span class="token operator">&lt;</span><span class="token operator">/</span>button<span class="token operator">&gt;</span>
<span class="token operator">&lt;</span><span class="token operator">!</span><span class="token operator">--</span>
<span class="token literal-property property">需求</span><span class="token operator">:</span> 点击某个按钮<span class="token punctuation">,</span> 提示<span class="token string">&quot;点击的是第n个按钮&quot;</span>
<span class="token operator">--</span><span class="token operator">&gt;</span>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span><span class="token operator">&gt;</span>
<span class="token keyword">var</span> btns <span class="token operator">=</span> document<span class="token punctuation">.</span><span class="token function">getElementsByTagName</span><span class="token punctuation">(</span><span class="token string">'button'</span><span class="token punctuation">)</span>
 <span class="token keyword">for</span><span class="token punctuation">(</span><span class="token keyword">var</span> i<span class="token operator">=</span><span class="token number">0</span><span class="token punctuation">,</span>length<span class="token operator">=</span>btns<span class="token punctuation">.</span>length<span class="token punctuation">;</span>i<span class="token operator">&lt;</span>length<span class="token punctuation">;</span>i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
   <span class="token keyword">var</span> btn <span class="token operator">=</span> btns<span class="token punctuation">[</span>i<span class="token punctuation">]</span>
   btn<span class="token punctuation">.</span>index <span class="token operator">=</span> i    <span class="token comment">//存到自身</span>
   btn<span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
     <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'第'</span><span class="token operator">+</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>index<span class="token operator">+</span><span class="token number">1</span><span class="token punctuation">)</span><span class="token operator">+</span><span class="token string">'个'</span><span class="token punctuation">)</span> <span class="token comment">//结果正确</span>
   <span class="token punctuation">}</span>
 <span class="token punctuation">}</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>    
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p>将其放在自己的身上，需要时自己找自己拿,这样就能解决</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180952212.png" alt="bibao3"></p> <ol start="3"><li>利用闭包</li></ol> <div class="language-HTML line-numbers-mode"><pre class="language-html"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试1<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试2<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span><span class="token punctuation">&gt;</span></span>测试3<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>

<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text/javascript<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
  <span class="token comment">// 利用闭包</span>
  <span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">var</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">,</span>length<span class="token operator">=</span>btns<span class="token punctuation">.</span>length<span class="token punctuation">;</span> i <span class="token operator">&lt;</span> length<span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token comment">//此处的j是局部的,它将传入的[i]存入局部的[j]中,这样就能实现效果 </span>
    <span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">j</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">var</span> btn <span class="token operator">=</span> btns<span class="token punctuation">[</span>j<span class="token punctuation">]</span>
      btn<span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
        <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'第'</span><span class="token operator">+</span><span class="token punctuation">(</span>j<span class="token operator">+</span><span class="token number">1</span><span class="token punctuation">)</span><span class="token operator">+</span><span class="token string">'个'</span><span class="token punctuation">)</span>
      <span class="token punctuation">}</span>
    <span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">(</span>i<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
</span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>  
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211180953148.png" alt="bibao4"></p> <p><strong>Ⅱ 常见的闭包</strong></p> <ol><li>将函数作为另一个函数的返回值</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">2</span>
  <span class="token keyword">function</span> <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    a<span class="token operator">++</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token keyword">return</span> fn2
<span class="token punctuation">}</span>
<span class="token keyword">var</span> f <span class="token operator">=</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 3</span>
<span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 4</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br></div></div><ol start="2"><li>将函数作为实参传递给另一个函数调用</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">showDelay</span><span class="token punctuation">(</span><span class="token parameter">msg<span class="token punctuation">,</span> time</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token function">alert</span><span class="token punctuation">(</span>msg<span class="token punctuation">)</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span> time<span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token function">showDelay</span><span class="token punctuation">(</span><span class="token string">'atguigu'</span><span class="token punctuation">,</span> <span class="token number">2000</span><span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br></div></div><ol start="3"><li>高阶函数与柯里化</li></ol> <p>​		有时候闭包在你甚至没有注意到它的时候就会出现，你可能已经看到了我们称为部分应用程序		的示例
​		当然如果你还不理解的话可以,可以完整的多看几次本笔记闭包知识点部分,或者结合上方 <a href="https://www.yuque.com/cessstudy/kak11d/il2gvw#%E2%85%A1-%E4%B8%BE%E4%B8%AA%E9%97%AD%E5%8C%85%E6%A0%97%E5%AD%90%E5%88%86%E6%9E%90%E7%90%86%E8%A7%A3" target="_blank" rel="noopener noreferrer">Ⅱ-举		个闭包栗子分析理解<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a> 进行理解</p> <p><strong>1、从 ES6 高阶箭头函数理解函数柯里化<code>(运用到闭包)</code></strong></p> <ol><li>首先看到了这样的一个例子</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">let</span> <span class="token function-variable function">add</span> <span class="token operator">=</span> <span class="token parameter">a</span> <span class="token operator">=&gt;</span> <span class="token parameter">b</span> <span class="token operator">=&gt;</span> a <span class="token operator">+</span> b
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br></div></div><ol start="2"><li>以上是一个很简单的相加函数，把它转化成 ES5 的写法如下</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">add</span><span class="token punctuation">(</span><span class="token parameter">a</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter">b</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">return</span> a <span class="token operator">+</span> b
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>

<span class="token keyword">var</span> add3 <span class="token operator">=</span> <span class="token function">add</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span> <span class="token comment">//add3表示一个指向函数的变量 可以当成函数调用名来用</span>
<span class="token function">add3</span><span class="token punctuation">(</span><span class="token number">4</span><span class="token punctuation">)</span> <span class="token operator">===</span> <span class="token number">3</span> <span class="token operator">+</span> <span class="token number">4</span> <span class="token comment">//true</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br></div></div><ol start="3"><li>再简化一下，可以写成如下形式：</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">let</span> <span class="token function-variable function">add</span> <span class="token operator">=</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter">a</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
<span class="token keyword">var</span> param <span class="token operator">=</span> a<span class="token punctuation">;</span>
<span class="token keyword">var</span> <span class="token function-variable function">innerFun</span> <span class="token operator">=</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter">b</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
<span class="token keyword">return</span> param <span class="token operator">+</span> b<span class="token punctuation">;</span>
<span class="token punctuation">}</span>
<span class="token keyword">return</span> innerFun<span class="token punctuation">;</span>
<span class="token punctuation">}</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><ol start="4"><li>虽然好像没什么意义，但是很显然上述使用了[闭包]，而且该函数的返回值是一个函数。其实，这就是高阶函数的定义：<code>以函数为参数或者返回值是函数的函数。</code></li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181127792.png" alt="bibao5"></p> <p><strong>2、柯里化</strong></p> <ol><li>图例</li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181128849.png" alt="keli1"></p> <ol start="2"><li>关键就是<code>理解柯里化</code>，其实可以把它理解成，柯里化后，<code>将第一个参数变量存在函数里面了(闭包)</code>，然后本来需要n个参数的函数可以变成只需要剩下的（n - 1个）参数就可以调用，比如</li></ol> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">let</span> <span class="token function-variable function">add</span> <span class="token operator">=</span> <span class="token parameter">x</span> <span class="token operator">=&gt;</span> <span class="token parameter">y</span> <span class="token operator">=&gt;</span> x <span class="token operator">+</span> y
<span class="token keyword">let</span> add2 <span class="token operator">=</span> <span class="token function">add</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span>

<span class="token operator">-</span><span class="token operator">*</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>
本来完成 add 这个操作，应该是这样调用
<span class="token keyword">let</span> <span class="token function-variable function">add</span> <span class="token operator">=</span> <span class="token punctuation">(</span><span class="token parameter">x<span class="token punctuation">,</span> y</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> x <span class="token operator">+</span> y
<span class="token function">add</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">,</span><span class="token number">3</span><span class="token punctuation">)</span>
<span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br></div></div><ol><li><p>而现在 add2 函数完成同样操作只需要一个参数，这在函数式编程中广泛应用。</p> <p><code>let add = x =&gt; y =&gt; x + y</code></p> <p><code>let add2 = add(2)</code></p></li> <li><p>详细解释一下，就是 add2 函数 等价于 有了 x 这个闭包变量的 y =&gt; x + y 函数,并且此时 x = 2，所以此时调用</p> <p><code>add2(3) === 2 + 3</code></p></li></ol> <p><strong>4、总结</strong></p> <ol><li><p>如果是<code>a =&gt; b =&gt; c =&gt; {xxx}</code>这种多次柯里化的,如何理解?</p> <p>理解:<code>前n - 1</code>次调用，其实是提前将参数传递进去，并没有调用最内层函数体，最后一次调用才会调用最内层函数体，并返回最内层函数体的返回值</p></li> <li><p>结合上文可知，这里的多个连续箭头（无论俩个箭头函数三个及以上）函数连在一起 就是在柯里化。所以连续箭头函数就是多次柯里化函数的 es6 写法。</p></li> <li><p><code>调用特点:</code> <code>let test = a =&gt; b =&gt; c =&gt; {xxx}</code></p></li></ol> <p>比如对于上面的<code>test</code>函数，它有 3 个箭头， 这个函数要被调用 3 次 <code>test(a)(b)(c)</code>，前两次调用只是在传递参数，只有最后依次调用才会返回 <code>{xxx}</code>代码段的返回值，并且在<code>{xxx}</code>代码段中可以调用 a,b,c</p> <p><strong>Ⅲ 闭包的作用</strong></p> <ol><li><p>使用函数内部的变量在函数执行完后，仍然存活在内存中（延长了局部变量的生命周期）</p></li> <li><p>让函数外部可以操作（读写）到函数内部的数据（变量/函数) 问题</p> <p>​	Q:</p></li> <li><p>函数执行完后, 函数内部声明的局部变量是否还存在?</p></li></ol> <p>​			一般是不存在，但在闭包中的变量可能存在</p> <ol start="2"><li>在函数外部能直接访问函数内部的局部变量吗?</li></ol> <p>​			不能，但我们可以通过闭包让外部操作它</p> <p><strong>Ⅳ 闭包的生命周期</strong></p> <ol><li>**产生：**在嵌套内部函数定义执行完时就产生了（不是在调用）</li> <li>**死亡：**在嵌套的内部函数成为垃圾对象时</li></ol> <ul><li>即没有人指向它时死亡，通常置为 <strong>null</strong>，当然指向其他也行，但不安全(容易污染变量)</li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 此时闭包就已经产生了(函数提升,实际上[fn2]提升到了第一行, 内部函数对象已经创建了)</span>
  <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">2</span>
  <span class="token keyword">function</span> <span class="token function">fn2</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//如果时[let fn2=function(){}]，那么在这行才会产生闭包</span>
    a<span class="token operator">++</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token keyword">return</span> fn2
<span class="token punctuation">}</span>
<span class="token keyword">var</span> f <span class="token operator">=</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 3</span>
<span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 4</span>
f <span class="token operator">=</span> <span class="token keyword">null</span> <span class="token comment">// 闭包死亡(包含闭包的函数对象成为垃圾对象)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br></div></div><p><strong>Ⅴ 闭包的应用</strong></p> <p>闭包的应用：定义JS模块</p> <ol><li>创建具有特定功能的 js 文件</li> <li>将所有的数据和功能都封装在一个函数内部(私有的)</li> <li>只向外暴露一个包信 n 个方法的对象或函数</li> <li>模块的使用者，只需要通过模块暴露的对象调用方法来实现对应的功能</li></ol> <p>No1.模块定义</p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">// myModule.js</span>
<span class="token keyword">function</span> <span class="token function">myModule</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 私有数据</span>
  <span class="token keyword">var</span> msg <span class="token operator">=</span> <span class="token string">'My atguigu'</span>
  <span class="token comment">// 操作数据的函数</span>
  <span class="token keyword">function</span> <span class="token function">doSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'doSomething() '</span><span class="token operator">+</span> msg<span class="token punctuation">.</span><span class="token function">toUpperCase</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token keyword">function</span> <span class="token function">doOtherthing</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'doOtherthing() '</span><span class="token operator">+</span>msg<span class="token punctuation">.</span><span class="token function">toLowerCase</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token comment">// 向外暴露对象(给外部使用的方法)</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    <span class="token literal-property property">doSomething</span><span class="token operator">:</span> doSomething<span class="token punctuation">,</span>
    <span class="token literal-property property">doOtherthing</span><span class="token operator">:</span> doOtherthing
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">-</span>
  <span class="token comment">// myModule2.js</span>
  <span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 私有数据</span>
  <span class="token keyword">var</span> msg <span class="token operator">=</span> <span class="token string">'My atguigu'</span>
  <span class="token comment">// 操作数据的函数</span>
  <span class="token keyword">function</span> <span class="token function">doSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'doSomething() '</span><span class="token operator">+</span> msg<span class="token punctuation">.</span><span class="token function">toUpperCase</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token keyword">function</span> <span class="token function">doOtherthing</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'doOtherthing() '</span><span class="token operator">+</span> msg<span class="token punctuation">.</span><span class="token function">toLowerCase</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token comment">// 向外暴露对象(给外部使用的方法)</span>
  window<span class="token punctuation">.</span>myModule2 <span class="token operator">=</span> <span class="token punctuation">{</span>
    <span class="token literal-property property">doSomething</span><span class="token operator">:</span> doSomething<span class="token punctuation">,</span>
    <span class="token literal-property property">doOtherthing</span><span class="token operator">:</span> doOtherthing
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span> 
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br><span class="line-number">29</span><br><span class="line-number">30</span><br><span class="line-number">31</span><br><span class="line-number">32</span><br><span class="line-number">33</span><br><span class="line-number">34</span><br><span class="line-number">35</span><br><span class="line-number">36</span><br></div></div><p>No2.模块调用</p> <p>二的方式好一点，可以在最后的括号内写 window，可以代码压缩</p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>  模块调用<span class="token number">1</span> <span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span> src<span class="token operator">=</span><span class="token string">&quot;myModule.js&quot;</span><span class="token operator">&gt;</span><span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span><span class="token operator">&gt;</span>
  <span class="token keyword">var</span> module <span class="token operator">=</span> <span class="token function">myModule</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
  module<span class="token punctuation">.</span><span class="token function">doSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
  module<span class="token punctuation">.</span><span class="token function">doOtherthing</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
<span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>  模块调用<span class="token number">2</span> <span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span><span class="token operator">--</span>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span> src<span class="token operator">=</span><span class="token string">&quot;myModule2.js&quot;</span><span class="token operator">&gt;</span><span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span><span class="token operator">&gt;</span>
  myModule2<span class="token punctuation">.</span><span class="token function">doSomething</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
  myModule2<span class="token punctuation">.</span><span class="token function">doOtherthing</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br></div></div><p><strong>Ⅵ 闭包的缺点及解决</strong></p> <p><strong>缺点</strong></p> <ol><li>函数执行完后，函数内的局部变量没有释放，占用内存时间会变长</li> <li>容易造成内存泄露</li></ol> <p><strong>解决</strong></p> <ol><li>能不用闭包就不用</li> <li>及时释放</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> arr <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Array</span><span class="token punctuation">(</span><span class="token number">100000</span><span class="token punctuation">)</span>   
  <span class="token keyword">function</span> <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>     
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>arr<span class="token punctuation">.</span>length<span class="token punctuation">)</span>   
  <span class="token punctuation">}</span>   
  <span class="token keyword">return</span> fn2 
<span class="token punctuation">}</span> 
<span class="token keyword">var</span> f <span class="token operator">=</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> 
<span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
f <span class="token operator">=</span> <span class="token keyword">null</span> <span class="token comment">// 让内部函数成为垃圾对象--&gt;回收闭包</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br></div></div><p>也可以调用时直接 f()() 直接运行调用即可--&gt;匿名函数，用完自动就销毁了</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181311836.png" alt="bibao6"></p> <p><strong>Ⅶ 内存溢出与内存泄露</strong></p> <p><strong>内存溢出</strong></p> <ul><li>一种程序运行出现的错误</li> <li>当程序运行需要的内存超过了剩余的内存时，就出抛出内存溢出的错误</li></ul> <p><strong>内存泄漏</strong></p> <ul><li>占用的内存没有及时释放</li> <li>内存泄露积累多了就容易导致内存溢出</li></ul> <p><strong>常见的内存泄露</strong></p> <ul><li>意外的全局变量</li> <li>没有及时清理的计时器或回调函数</li> <li>闭包</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token operator">&lt;</span>script type<span class="token operator">=</span><span class="token string">&quot;text/javascript&quot;</span><span class="token operator">&gt;</span>
  <span class="token comment">// 1. 内存溢出</span>
  <span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
  <span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">var</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> <span class="token number">10000</span><span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    obj<span class="token punctuation">[</span>i<span class="token punctuation">]</span> <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Array</span><span class="token punctuation">(</span><span class="token number">10000000</span><span class="token punctuation">)</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'-----'</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>

  <span class="token comment">// 2. 内存泄露</span>
  <span class="token comment">// 意外的全局变量</span>
  <span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    a <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Array</span><span class="token punctuation">(</span><span class="token number">10000000</span><span class="token punctuation">)</span>  <span class="token comment">// 不使用 let const var 声明，实际是挂载到 window 上的</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>a<span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
  <span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>

  <span class="token comment">// 没有及时清理的计时器或回调函数</span>
  <span class="token keyword">var</span> intervalId <span class="token operator">=</span> <span class="token function">setInterval</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">// 启动循环定时器后不清理</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'----'</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span>

  <span class="token comment">// clearInterval(intervalId)</span>

  <span class="token comment">// 闭包</span>
  <span class="token keyword">function</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token number">4</span>
    <span class="token keyword">function</span> <span class="token function">fn2</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token operator">++</span>a<span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
    <span class="token keyword">return</span> fn2
  <span class="token punctuation">}</span>
  <span class="token keyword">var</span> f <span class="token operator">=</span> <span class="token function">fn1</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
  <span class="token function">f</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
  <span class="token comment">// f = null</span>

<span class="token operator">&lt;</span><span class="token operator">/</span>script<span class="token operator">&gt;</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br><span class="line-number">29</span><br><span class="line-number">30</span><br><span class="line-number">31</span><br><span class="line-number">32</span><br><span class="line-number">33</span><br><span class="line-number">34</span><br><span class="line-number">35</span><br><span class="line-number">36</span><br><span class="line-number">37</span><br></div></div><p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181312564.png" alt="leak1"></p> <p><strong>Ⅷ 相关面试题</strong></p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 代码片段一  --&gt;没有产生闭包:因为内部函数没有调用外部变量</span>
<span class="token keyword">var</span> name <span class="token operator">=</span> <span class="token string">&quot;The Window&quot;</span><span class="token punctuation">;</span>
<span class="token keyword">var</span> object <span class="token operator">=</span> <span class="token punctuation">{</span>
  <span class="token literal-property property">name</span> <span class="token operator">:</span> <span class="token string">&quot;My Object&quot;</span><span class="token punctuation">,</span>
  <span class="token function-variable function">getNameFunc</span> <span class="token operator">:</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
    <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
      <span class="token keyword">return</span> <span class="token keyword">this</span><span class="token punctuation">.</span>name<span class="token punctuation">;</span>
    <span class="token punctuation">}</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token function">alert</span><span class="token punctuation">(</span>object<span class="token punctuation">.</span><span class="token function">getNameFunc</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span>  <span class="token comment">// the window 函数体的this指向是window，没有闭包</span>
<span class="token comment">//函数体的this是window</span>

<span class="token comment">//代码片段二</span>
<span class="token keyword">var</span> name2 <span class="token operator">=</span> <span class="token string">&quot;The Window&quot;</span><span class="token punctuation">;</span>
<span class="token keyword">var</span> object2 <span class="token operator">=</span> <span class="token punctuation">{</span>
  <span class="token literal-property property">name2</span> <span class="token operator">:</span> <span class="token string">&quot;My Object&quot;</span><span class="token punctuation">,</span>
  <span class="token function-variable function">getNameFunc</span> <span class="token operator">:</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
    <span class="token comment">// 此处的this指向是 getNameFunc，他是对象中的属性，所以that指向就是object</span>
    <span class="token keyword">var</span> that <span class="token operator">=</span> <span class="token keyword">this</span><span class="token punctuation">;</span>
    <span class="token keyword">return</span> <span class="token keyword">function</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
      <span class="token comment">//此处用的是保存的  that</span>
      <span class="token keyword">return</span> that<span class="token punctuation">.</span>name2<span class="token punctuation">;</span>
    <span class="token punctuation">}</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span><span class="token punctuation">;</span>
<span class="token function">alert</span><span class="token punctuation">(</span>object2<span class="token punctuation">.</span><span class="token function">getNameFunc</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token punctuation">)</span><span class="token punctuation">;</span> <span class="token comment">// my object 有闭包</span>


● 
<span class="token literal-property property">●</span> <span class="token operator">:</span>因为内部函数没有调用外部变量

● <span class="token keyword">this</span>指向是调用它的<span class="token punctuation">[</span>getNameFunc<span class="token punctuation">]</span><span class="token punctuation">,</span>他是对象中的属性<span class="token punctuation">,</span>所以<span class="token keyword">this</span>指向就是object
● 产生了闭包
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br><span class="line-number">29</span><br><span class="line-number">30</span><br><span class="line-number">31</span><br><span class="line-number">32</span><br><span class="line-number">33</span><br><span class="line-number">34</span><br></div></div><div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">fun</span><span class="token punctuation">(</span><span class="token parameter">n<span class="token punctuation">,</span> o</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>o<span class="token punctuation">)</span>
  <span class="token keyword">return</span> <span class="token punctuation">{</span>
    <span class="token function-variable function">fun</span><span class="token operator">:</span><span class="token keyword">function</span><span class="token punctuation">(</span><span class="token parameter">m</span><span class="token punctuation">)</span><span class="token punctuation">{</span>
      <span class="token keyword">return</span> <span class="token function">fun</span><span class="token punctuation">(</span>m<span class="token punctuation">,</span> n<span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token keyword">var</span> a <span class="token operator">=</span> <span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">0</span><span class="token punctuation">)</span> <span class="token comment">//undefined</span>
a<span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span>  <span class="token comment">//0</span>
a<span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span>  <span class="token comment">//0	</span>
a<span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span>  <span class="token comment">//0</span>

<span class="token keyword">var</span> b <span class="token operator">=</span> <span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span> <span class="token comment">//undefined 0 1 2</span>

<span class="token keyword">var</span> c <span class="token operator">=</span> <span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span> <span class="token comment">//undefined  0</span>
c<span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span><span class="token comment">//1 --&gt;经过上方定义后 n固定为1</span>
c<span class="token punctuation">.</span><span class="token function">fun</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span><span class="token comment">//1 --&gt;此处是陷阱!!!  一直没有改到n,所以一直是1</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br></div></div><h3 id="三、-面向对象高级"><a href="#三、-面向对象高级" class="header-anchor">#</a> 三、 面向对象高级</h3> <p>此部分要求你对前方<strong>函数高级部分的1、原型与原型链</strong>比较熟悉,如果掌握不够好理解会相对困难</p> <h3 id="_3-1-对象创建模式"><a href="#_3-1-对象创建模式" class="header-anchor">#</a> 3.1 对象创建模式</h3> <p><strong>Ⅰ-Object构造函数模式</strong></p> <ul><li>套路：先创建空 Object 对象，再动态添加属性/方法</li> <li>适用场景：起始时不确定对象内部数据</li> <li>问题：语句太多</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">// 一个人: name:&quot;Tom&quot;, age: 12</span>
<span class="token keyword">var</span> p <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Object</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
p <span class="token operator">=</span> <span class="token punctuation">{</span><span class="token punctuation">}</span>
p<span class="token punctuation">.</span>name <span class="token operator">=</span> <span class="token string">'Tom'</span>
p<span class="token punctuation">.</span>age <span class="token operator">=</span> <span class="token number">12</span>
p<span class="token punctuation">.</span><span class="token function-variable function">setName</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
<span class="token punctuation">}</span>

console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p<span class="token punctuation">.</span>name<span class="token punctuation">,</span> p<span class="token punctuation">.</span>age<span class="token punctuation">)</span>
p<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'Bob'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p<span class="token punctuation">.</span>name<span class="token punctuation">,</span> p<span class="token punctuation">.</span>age<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><p><strong>Ⅱ-对象字面量模式</strong></p> <ul><li>套路：使用<code>{ }</code>创建对象，同时指定属性/方法</li> <li>适用场景：起始时对象内部数据是确定的</li> <li>问题：如果创建多个对象，有重复代码</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token keyword">var</span> p <span class="token operator">=</span> <span class="token punctuation">{</span>
  <span class="token literal-property property">name</span><span class="token operator">:</span> <span class="token string">'Tom'</span><span class="token punctuation">,</span>
  <span class="token literal-property property">age</span><span class="token operator">:</span> <span class="token number">12</span><span class="token punctuation">,</span>
  <span class="token function-variable function">setName</span><span class="token operator">:</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>

console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p<span class="token punctuation">.</span>name<span class="token punctuation">,</span> p<span class="token punctuation">.</span>age<span class="token punctuation">)</span>
p<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'JACK'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p<span class="token punctuation">.</span>name<span class="token punctuation">,</span> p<span class="token punctuation">.</span>age<span class="token punctuation">)</span>

<span class="token keyword">var</span> p2 <span class="token operator">=</span> <span class="token punctuation">{</span>  <span class="token comment">// 如果创建多个对象代码很重复</span>
  <span class="token literal-property property">name</span><span class="token operator">:</span> <span class="token string">'Bob'</span><span class="token punctuation">,</span>
  <span class="token literal-property property">age</span><span class="token operator">:</span> <span class="token number">13</span><span class="token punctuation">,</span>
  <span class="token function-variable function">setName</span><span class="token operator">:</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br></div></div><p><strong>Ⅲ 工厂模式</strong></p> <ul><li>套路：通过工厂函数动态创建对象并返回</li> <li>适用场景：需要创建多个对象</li> <li>问题：对象没有一个具体的类型, 都是Object类型</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">//返回一个对象的函数===&gt;工厂函数</span>
<span class="token keyword">function</span> <span class="token function">createPerson</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> 
  <span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span>
    <span class="token literal-property property">name</span><span class="token operator">:</span> name<span class="token punctuation">,</span>
    <span class="token literal-property property">age</span><span class="token operator">:</span> age<span class="token punctuation">,</span>
    <span class="token function-variable function">setName</span><span class="token operator">:</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
    <span class="token punctuation">}</span>
  <span class="token punctuation">}</span>
  <span class="token keyword">return</span> obj
<span class="token punctuation">}</span>

<span class="token comment">// 创建2个人</span>
<span class="token keyword">var</span> p1 <span class="token operator">=</span> <span class="token function">createPerson</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span>
<span class="token keyword">var</span> p2 <span class="token operator">=</span> <span class="token function">createPerson</span><span class="token punctuation">(</span><span class="token string">'Bob'</span><span class="token punctuation">,</span> <span class="token number">13</span><span class="token punctuation">)</span>

<span class="token comment">// p1/p2是Object类型</span>

<span class="token keyword">function</span> <span class="token function">createStudent</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> price</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> obj <span class="token operator">=</span> <span class="token punctuation">{</span>
    <span class="token literal-property property">name</span><span class="token operator">:</span> name<span class="token punctuation">,</span>
    <span class="token literal-property property">price</span><span class="token operator">:</span> price
  <span class="token punctuation">}</span>
  <span class="token keyword">return</span> obj
<span class="token punctuation">}</span>
<span class="token keyword">var</span> s <span class="token operator">=</span> <span class="token function">createStudent</span><span class="token punctuation">(</span><span class="token string">'张三'</span><span class="token punctuation">,</span> <span class="token number">12000</span><span class="token punctuation">)</span>
<span class="token comment">// s也是Object</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br></div></div><p><strong>Ⅳ 自定义构造函数模式</strong></p> <ul><li>套路：自定义构造函数，通过 new 创建对象</li> <li>适用场景：需要创建多个类型确定的对象，与上方工厂模式有所对比</li> <li>问题：每个对象都有相同的数据, 浪费内存</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">//定义类型</span>
<span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>age <span class="token operator">=</span> age
  <span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function-variable function">setName</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
    <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token punctuation">}</span>
<span class="token punctuation">}</span>
<span class="token keyword">var</span> p1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">12</span><span class="token punctuation">)</span>
p1<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'Jack'</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1<span class="token punctuation">.</span>name<span class="token punctuation">,</span> p1<span class="token punctuation">.</span>age<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1 <span class="token keyword">instanceof</span> <span class="token class-name">Person</span><span class="token punctuation">)</span>

<span class="token keyword">function</span> <span class="token function">Student</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> price</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>price <span class="token operator">=</span> price
<span class="token punctuation">}</span>
<span class="token keyword">var</span> s <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Student</span><span class="token punctuation">(</span><span class="token string">'Bob'</span><span class="token punctuation">,</span> <span class="token number">13000</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>s <span class="token keyword">instanceof</span> <span class="token class-name">Student</span><span class="token punctuation">)</span>

<span class="token keyword">var</span> p2 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'JACK'</span><span class="token punctuation">,</span> <span class="token number">23</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1<span class="token punctuation">,</span> p2<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br></div></div><p><strong>Ⅴ 构造函数 + 原型的组合模式</strong></p> <p>最好用这个写法</p> <ul><li>套路：自定义构造函数, 属性在函数中初始化，方法添加到原型上</li> <li>适用场景：需要创建多个类型确定的对象</li> <li>放在原型上可以节省空间（只需要加载一遍方法）</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">//在构造函数中只初始化一般函数</span>
<span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> 
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>age <span class="token operator">=</span> age
<span class="token punctuation">}</span>
<span class="token class-name">Person</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">setName</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
<span class="token punctuation">}</span>

<span class="token keyword">var</span> p1 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">23</span><span class="token punctuation">)</span>
<span class="token keyword">var</span> p2 <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token string">'Jack'</span><span class="token punctuation">,</span> <span class="token number">24</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>p1<span class="token punctuation">,</span> p2<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><h3 id="_3-2-继承模式"><a href="#_3-2-继承模式" class="header-anchor">#</a> 3.2 继承模式</h3> <p><strong>Ⅰ 原型链继承</strong></p> <p>1.套路</p> <ul><li>定义父类型构造函数</li> <li>给父类型的原型添加方法</li> <li>定义子类型的构造函数</li> <li>创建父类型的实例对象赋值给子类型的原型</li> <li>将子类型原型的构造属性设置为子类型</li> <li>给子类型原型添加方法</li> <li>创建子类型的对象，可以调用父类型的方法</li></ul> <ol start="2"><li>关键</li></ol> <ul><li><font color="#d00"><strong>子类型的原型为父类型的一个实例对象</strong></font></li></ul> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">// 父类型</span>
<span class="token keyword">function</span> <span class="token function">Supper</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>supProp <span class="token operator">=</span> <span class="token string">'父亲的原型链'</span>
<span class="token punctuation">}</span>
<span class="token comment">// 给父类型的原型上增加一个 showSupperProp 方法，打印自身 subProp</span>
<span class="token class-name">Supper</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">showSupperProp</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>supProp<span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token comment">// 子类型</span>
<span class="token keyword">function</span> <span class="token function">Sub</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>subProp <span class="token operator">=</span> <span class="token string">'儿子的原型链'</span>
<span class="token punctuation">}</span>
<span class="token comment">// 子类型的原型为父类型的一个实例对象</span>
<span class="token class-name">Sub</span><span class="token punctuation">.</span>prototype <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Supper</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token comment">// 让子类型的原型的constructor指向子类型</span>
<span class="token comment">// 如果不加，其构造函数找的[`new Supper()`]时从顶层Object继承来的构造函数,指向[`Supper()`]</span>
<span class="token class-name">Sub</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>constructor <span class="token operator">=</span> Sub
<span class="token comment">// 给子类型的原型上增加一个 showSubProp 方法，打印自身 subProp</span>
<span class="token class-name">Sub</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">showSubProp</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">.</span>subProp<span class="token punctuation">)</span>
<span class="token punctuation">}</span>

<span class="token keyword">var</span> sub <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Sub</span><span class="token punctuation">(</span><span class="token punctuation">)</span>

sub<span class="token punctuation">.</span><span class="token function">showSupperProp</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 父亲的原型链</span>
sub<span class="token punctuation">.</span><span class="token function">showSubProp</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 儿子的原型链</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>sub<span class="token punctuation">)</span>  
<span class="token comment">/**
  Sub {subProp: &quot;儿子的原型链&quot;}
  subProp: &quot;儿子的原型链&quot;
  __proto__: Supper
  constructor: ƒ Sub()
  showSubProp: ƒ ()
  supProp: &quot;父亲的原型链&quot;
	__proto__: Object
*/</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br><span class="line-number">29</span><br><span class="line-number">30</span><br><span class="line-number">31</span><br><span class="line-number">32</span><br><span class="line-number">33</span><br><span class="line-number">34</span><br><span class="line-number">35</span><br><span class="line-number">36</span><br><span class="line-number">37</span><br><span class="line-number">38</span><br></div></div><p>示例图</p> <p>​	注意：此图中没有体现 constructor 构造函数，会在下方构造函数补充处指出</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181320002.png" alt="gouzaohanshu"></p> <p><strong>Ⅱ 借用构造函数继承（假的</strong></p> <p><strong>套路</strong></p> <ul><li>定义父类型构造函数</li> <li>定义子类型构造函数</li> <li>在子类型构造函数中调用父类型构造</li></ul> <p><strong>关键</strong></p> <ul><li>在子类型构造函数中通用call()调用父类型构造函数</li></ul> <p><strong>作用</strong></p> <ul><li>能借用父类中的构造方法，但是不灵活</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>age <span class="token operator">=</span> age
<span class="token punctuation">}</span>
<span class="token keyword">function</span> <span class="token function">Student</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age<span class="token punctuation">,</span> price</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token comment">// 此处利用call(),将 [Student]的this传递给Person构造函数</span>
  <span class="token function">Person</span><span class="token punctuation">.</span><span class="token function">call</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">,</span> name<span class="token punctuation">,</span> age<span class="token punctuation">)</span>  <span class="token comment">// 相当于: this.Person(name, age)</span>
  <span class="token comment">/*this.name = name
 this.age = age*/</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>price <span class="token operator">=</span> price
<span class="token punctuation">}</span>

<span class="token keyword">var</span> s <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Student</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">20</span><span class="token punctuation">,</span> <span class="token number">14000</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>s<span class="token punctuation">.</span>name<span class="token punctuation">,</span> s<span class="token punctuation">.</span>age<span class="token punctuation">,</span> s<span class="token punctuation">.</span>price<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br></div></div><p>Person 中的 this 是动态变化的,在[Student]中利用[Person.call(this, name, age)]改变了其this指向,所以可以实现此效果</p> <p><strong>Ⅲ 组合继承</strong></p> <p>原型链 + 借用构造函数的组合继承</p> <ol><li>利用原型链实现对父类型对象的方法继承</li> <li>利用super()借用父类型构建函数初始化相同属性</li></ol> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">function</span> <span class="token function">Person</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
  <span class="token keyword">this</span><span class="token punctuation">.</span>age <span class="token operator">=</span> age
<span class="token punctuation">}</span>
<span class="token class-name">Person</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">setName</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">name</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>name <span class="token operator">=</span> name
<span class="token punctuation">}</span>

<span class="token keyword">function</span> <span class="token function">Student</span><span class="token punctuation">(</span><span class="token parameter">name<span class="token punctuation">,</span> age<span class="token punctuation">,</span> price</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token function">Person</span><span class="token punctuation">.</span><span class="token function">call</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">,</span> name<span class="token punctuation">,</span> age<span class="token punctuation">)</span>  <span class="token comment">// 为了得到属性</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>price <span class="token operator">=</span> price
<span class="token punctuation">}</span>
<span class="token class-name">Student</span><span class="token punctuation">.</span>prototype <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Person</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token comment">// 为了能看到父类型的方法</span>
<span class="token class-name">Student</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span>constructor <span class="token operator">=</span> Student <span class="token comment">// 修正constructor属性</span>
<span class="token class-name">Student</span><span class="token punctuation">.</span>prototype<span class="token punctuation">.</span><span class="token function-variable function">setPrice</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">price</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">this</span><span class="token punctuation">.</span>price <span class="token operator">=</span> price
<span class="token punctuation">}</span>

<span class="token keyword">var</span> s <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Student</span><span class="token punctuation">(</span><span class="token string">'Tom'</span><span class="token punctuation">,</span> <span class="token number">24</span><span class="token punctuation">,</span> <span class="token number">15000</span><span class="token punctuation">)</span>
s<span class="token punctuation">.</span><span class="token function">setName</span><span class="token punctuation">(</span><span class="token string">'Bob'</span><span class="token punctuation">)</span>
s<span class="token punctuation">.</span><span class="token function">setPrice</span><span class="token punctuation">(</span><span class="token number">16000</span><span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span>s<span class="token punctuation">.</span>name<span class="token punctuation">,</span> s<span class="token punctuation">.</span>age<span class="token punctuation">,</span> s<span class="token punctuation">.</span>price<span class="token punctuation">)</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br></div></div><h2 id="四、线程机制与事件机制"><a href="#四、线程机制与事件机制" class="header-anchor">#</a> 四、线程机制与事件机制</h2> <h3 id="_4-1-进程与线程"><a href="#_4-1-进程与线程" class="header-anchor">#</a> 4-1 进程与线程</h3> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181345209.png" alt="进程线程"></p> <p><strong>Ⅰ- 进程</strong></p> <ol><li>程序的一次执行,它占有一片独有的内存空间</li> <li>可以通过windows任务管理器查看进程
<ul><li>可以看出每个程序的内存空间是相互独立的</li></ul></li></ol> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181346484.png" alt="进程1"></p> <p><strong>Ⅱ-线程</strong></p> <p>概念</p> <ul><li>是进程内的一个独立执行单元</li> <li>是程序执行的一个完整流程</li> <li>是CPU的最小的调度单元</li></ul> <p><strong>Ⅲ-进程与线程</strong></p> <ol><li>应用程序必须运行在某个进程的某个线程上</li> <li>一个进程中至少有一个运行的线程:主线程 --&gt;进程启动后自动创建</li> <li>一个进程中也可以同时运行多个线程:此时我们会说这个程序是多线程运行的</li> <li>多个进程之间的数据是不能直接共享的 --&gt;内存相互独立(隔离)</li> <li>线程池(thread pool):保存多个线程对象的容器,实现线程对象的反复利用</li></ol> <p><strong>Ⅳ-引出的问题</strong></p> <p><strong>① 何为多进程与多线程?</strong></p> <p>多进程运行: 一应用程序可以同时启动多个实例运行
多线程: 在一个进程内, 同时有多个线程运行</p> <p><strong>②比较单线程与多线程?</strong></p> <p>多线程:</p> <ul><li>优点:能有效提升CPU的利用率</li> <li>缺点</li> <li>创建多线程开销</li> <li>线程间切换开销</li> <li>死锁与状态同步问题</li></ul> <p>单线程:</p> <ul><li>优点:顺序编程简单易懂</li> <li>缺点:效率低</li></ul> <p><strong>③ JS是单线程还是多线程?</strong></p> <p>JS是单线程运行的 , 但使用H5中的 Web Workers可以多线程运行</p> <ul><li>只能由一个线程去操作DOM界面</li> <li>具体原因可看下方<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/HTML+CSS+JS%E5%9F%BA%E7%A1%80%E7%AC%94%E8%AE%B0/JavaScript%E7%AC%94%E8%AE%B0#3%E3%80%81JS%E6%98%AF%E5%8D%95%E7%BA%BF%E7%A8%8B%E7%9A%84" target="_blank" rel="noopener noreferrer">3、JS是单线程的<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>部分给出的详解</li></ul> <p><strong>④ 浏览器运行是单线程还是多线程?</strong></p> <p>都是多线程运行的</p> <p><strong>⑤ 浏览器运行是单进程还是多进程?</strong></p> <p>有的是单进程:</p> <ul><li>firefox</li> <li>老版IE</li></ul> <p>有的是多进程:</p> <ul><li>chrome</li> <li>新版IE</li></ul> <p>如何查看浏览器是否是多进程运行的呢? 任务管理器--&gt;进程</p> <h3 id="_4-2-浏览器内核"><a href="#_4-2-浏览器内核" class="header-anchor">#</a> 4-2 浏览器内核</h3> <p>支撑浏览器运行的最核心的程序</p> <p><strong>Ⅰ-不同浏览器的内核</strong></p> <ul><li>Chrome, Safari : webkit</li> <li>firefox : Gecko</li> <li>IE : Trident</li> <li>360,搜狗等国内浏览器: Trident + webkit</li></ul> <p><strong>Ⅱ-内核由什么模块组成?</strong></p> <p>主线程</p> <ol><li>js引擎模块 : 负责js程序的编译与运行</li> <li>html,css文档解析模块 : 负责页面文本的解析(拆解)</li> <li>dom/css模块 : 负责dom/css在内存中的相关处理</li> <li>布局和渲染模块 : 负责页面的布局和效果的绘制</li> <li>布局和渲染模块 : 负责页面的布局和效果的绘制</li></ol> <p>分线程</p> <ul><li>定时器模块 : 负责定时器的管理</li> <li>网络请求模块 : 负责服务器请求(常规/Ajax)</li> <li>事件响应模块 : 负责事件的管理</li></ul> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181351585.png" alt="内核"></p> <h3 id="_4-3-定时器引发的思考"><a href="#_4-3-定时器引发的思考" class="header-anchor">#</a> 4-3 定时器引发的思考</h3> <div class="language-html line-numbers-mode"><pre class="language-html"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>body</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span> <span class="token attr-name">id</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>btn<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>启动定时器<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text/javascript<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
    document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'btn'</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">var</span> start <span class="token operator">=</span> Date<span class="token punctuation">.</span><span class="token function">now</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'启动定时器前...'</span><span class="token punctuation">)</span>
      <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
        console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'定时器执行了'</span><span class="token punctuation">,</span> Date<span class="token punctuation">.</span><span class="token function">now</span><span class="token punctuation">(</span><span class="token punctuation">)</span><span class="token operator">-</span>start<span class="token punctuation">)</span> <span class="token comment">//定时器并不能保证真正定时执行,一般会延迟一丁点</span>
      <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">200</span><span class="token punctuation">)</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'启动定时器后...'</span><span class="token punctuation">)</span>
      <span class="token comment">// 做一个长时间的工作</span>
      <span class="token keyword">for</span> <span class="token punctuation">(</span><span class="token keyword">var</span> i <span class="token operator">=</span> <span class="token number">0</span><span class="token punctuation">;</span> i <span class="token operator">&lt;</span> <span class="token number">1000000000</span><span class="token punctuation">;</span> i<span class="token operator">++</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//会造成定时器延长很长时间</span>
        <span class="token operator">...</span>
      <span class="token punctuation">}</span>
      <span class="token punctuation">}</span>
  </span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>body</span><span class="token punctuation">&gt;</span></span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br></div></div><p><strong>Ⅰ-定时器真是定时执行的吗?</strong></p> <ul><li>定时器并不能保证真正定时执行</li> <li>一般会延迟一丁点(可以接受), 也有可能延迟很长时间(不能接受)</li></ul> <p><strong>Ⅱ-定时器回调函数是在分线程执行的吗?</strong></p> <ul><li>在主线程执行的, JS是单线程的</li></ul> <p><strong>Ⅲ-定时器是如何实现的?</strong></p> <ul><li>事件循环模型，在下方给出详解</li></ul> <h3 id="_4-3-js是单线程的"><a href="#_4-3-js是单线程的" class="header-anchor">#</a> 4-3 JS是单线程的</h3> <p><strong>Ⅰ-如何证明JS执行是单线程的</strong></p> <ul><li><code>setTimeout()</code>的回调函数是在主线程执行的</li> <li>定时器回调函数只有在运行栈中的代码全部执行完后才有可能执行</li></ul> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">// 如何证明JS执行是单线程的</span>
<span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//4. 在将[timeout 1111]弹窗关闭后,再等一秒 执行此处</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout 2222'</span><span class="token punctuation">)</span>
  <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'22222222'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">2000</span><span class="token punctuation">)</span>
<span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//3. 过了一秒后 打印 timeout 1111并弹窗,此处如果不将弹窗关闭,不会继续执行上方222</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout 1111'</span><span class="token punctuation">)</span>
  <span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'1111111'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">1000</span><span class="token punctuation">)</span>
<span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//2. 然后打印timeout() 00000</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout() 00000'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span>
<span class="token keyword">function</span> <span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//1. fn()</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'fn()'</span><span class="token punctuation">)</span>
<span class="token punctuation">}</span>
<span class="token function">fn</span><span class="token punctuation">(</span><span class="token punctuation">)</span>
<span class="token comment">//----------------------</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'alert()之前'</span><span class="token punctuation">)</span>
<span class="token function">alert</span><span class="token punctuation">(</span><span class="token string">'------'</span><span class="token punctuation">)</span> <span class="token comment">//暂停当前主线程的执行, 同时暂停计时, 点击确定后, 恢复程序执行和计时</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'alert()之后'</span><span class="token punctuation">)</span>
流程结果
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br></div></div><p>==流程结果==</p> <ol><li><p>先打印了[fn()],然后马上就打印了[timeout() 00000]</p></li> <li><p>过了一秒后 打印 timeout 1111并弹窗,此处如果不将弹窗关闭,不会继续执行上方222</p></li> <li><p>在将[timeout 1111]弹窗关闭后,再等一秒 执行此处</p> <ul><li><p>问:为何明明写的是2秒,却关闭上一个弹窗<code>再过一秒</code>就执行?</p></li> <li><p>解:并不是关闭后再计算的,而是一起计算的,alert只是暂停了主线程执行</p></li></ul></li></ol> <p><strong>Ⅱ-JS引擎执行代码的基本流程与代码分类</strong></p> <p>代码分类</p> <ul><li>初始化代码</li> <li>回调代码</li></ul> <p>js引擎执行代码的基本流程</p> <ol><li>先执行初始化代码: 包含一些特别的代码 回调函数(异步执行)</li> <li>设置定时器</li> <li>绑定事件监听</li> <li>发送ajax请求</li> <li>后面在某个时刻才会执行回调代码</li></ol> <p><strong>Ⅲ-为什么js要用单线程模式，而不用多线程模式?</strong></p> <ol><li>JavaScript的单线程，与它的用途有关。</li> <li>作为浏览器脚本语言，JavaScript的主要用途是与用户互动，以及操作DOM</li> <li>这决定了它只能是单线程，否则会带来很复杂的同步问题
<ul><li>举个栗子:如果我们要实现更新页面上一个dom节点然后删除,用单线程是没问题的</li> <li>但是如果多线程,当我删除线程先删除了dom节点,更新线程要去更新的时候就会出错</li></ul></li></ol> <h3 id="_4-4-事件循环模型-event-loop-机制"><a href="#_4-4-事件循环模型-event-loop-机制" class="header-anchor">#</a> 4-4 事件循环模型(Event Loop)机制</h3> <p><strong>Ⅰ-概念引出</strong></p> <p>我们都知道，<code>javascript从诞生之日起就是一门单线程的非阻塞的脚本语言</code>。这是由其最初的用途来决定的：<code>与浏览器交互</code>。
单线程意味着，javascript代码在执行的任何时候，都只有一个主线程来处理所有的任务。
<code>非阻塞:</code>
而非阻塞则是当代码需要进行一项异步任务（无法立刻返回结果，需要花一定时间才能返回的任务，如I/O事件）的时候，主线程会挂起（pending）这个任务，然后在异步任务返回结果的时候再根据一定规则去执行相应的回调。
<code>单线程是必要的:</code>
也是javascript这门语言的基石，原因之一在其最初也是最主要的执行环境——浏览器中，我们需要进行各种各样的dom操作。试想一下 如果javascript是多线程的，那么当两个线程同时对dom进行一项操作，例如一个向其添加事件，而另一个删除了这个dom，此时该如何处理呢？因此，为了保证不会 发生类似于这个例子中的情景，javascript选择只用一个主线程来执行代码，这样就保证了程序执行的一致性。
当然，现如今人们也意识到，单线程在保证了执行顺序的同时也限制了javascript的效率，因此开发出了<code>web workers</code>技术。这项技术号称可以让javaScript成为一门多线程语言。
然而，使用web workers技术开的多线程有着诸多限制，例如：<code>所有新线程都受主线程的完全控制，不能独立执行</code>。这意味着这些“线程” 实际上应属于主线程的子线程。另外，这些子线程并没有执行I/O操作的权限，只能为主线程分担一些诸如计算等任务。所以严格来讲这些线程并没有完整的功能，也因此这项技术并非改变了javascript语言的单线程本质。
可以预见，未来的javascript也会一直是一门单线程的语言。
话说回来，前面提到javascript的另一个特点是<code>“非阻塞”</code>，那么javascript引擎到底是如何实现的这一点呢？
答案就是——event loop（事件循环）。
<strong>注：虽然nodejs中的也存在与传统浏览器环境下的相似的事件循环。然而两者间却有着诸多不同，故把两者分开，单独解释。</strong></p> <p><strong>Ⅱ-浏览器环境下JS引擎的事件循环机制</strong></p> <p><strong>① 执行栈概念</strong></p> <p>执行上下文栈详情可以看上方笔记 --&gt;<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/HTML+CSS+JS%E5%9F%BA%E7%A1%80%E7%AC%94%E8%AE%B0/JavaScript%E7%AC%94%E8%AE%B0#2%E3%80%81%E6%89%A7%E8%A1%8C%E4%B8%8A%E4%B8%8B%E6%96%87%E4%B8%8E%E6%89%A7%E8%A1%8C%E4%B8%8A%E4%B8%8B%E6%96%87%E6%A0%88" target="_blank" rel="noopener noreferrer">函数高级的2、执行上下文与执行上下文栈<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>,此处继续进行一次概述加深理解
当javascript代码执行的时候会将不同的变量存于内存中的不同位置：<code>堆（heap）</code>和<code>栈（stack）</code>中来加以区分。其中，堆里存放着一些对象。而栈中则存放着一些基础类型变量以及对象的指针。 但是我们这里说的执行栈和上面这个栈的意义却有些不同。
执行栈:
当我们调用一个方法的时候，js会生成一个与这个方法对应的执行环境（context），又叫执行上下文。这个执行环境中存在着这个方法的私有作用域、上层作用域的指向、方法的参数，这个作用域中定义的变量以及这个作用域的this对象。 而当一系列方法被依次调用的时候，因为js是单线程的，同一时间只能执行一个方法，于是这些方法被排队在一个单独的地方。这个地方被称为执行栈。
当一个脚本第一次执行的时候，js引擎会解析这段代码，并将其中的同步代码按照执行顺序加入执行栈中，然后从头开始执行。如果当前执行的是一个方法，那么js会向执行栈中添加这个方法的执行环境，然后进入这个执行环境继续执行其中的代码。当这个执行环境中的代码 执行完毕并返回结果后，js会退出这个执行环境并把这个执行环境销毁，回到上一个方法的执行环境。这个过程反复进行，直到执行栈中的代码全部执行完毕。</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181404569.gif" alt="栈"></p> <p>从图片可知，一个方法执行会向执行栈中加入这个方法的执行环境，在这个执行环境中还可以调用其他方法，甚至是自己，其结果不过是在执行栈中再添加一个执行环境。这个过程可以是无限进行下去的，<code>除非发生了栈溢出，即超过了所能使用内存的最大值</code>。
以上的过程说的都是同步代码的执行。那么当一个异步代码（如发送ajax请求数据）执行后会如何呢？
刚刚说过js的另一大特点是非阻塞，实现这一点的关键在于下面要说的这项机制——<code>事件队列（Task Queue）</code>。</p> <p><strong>② 事件队列（Task Queue）</strong></p> <p>JS引擎遇到一个异步事件后并不会一直等待其返回结果，而是会将这个事件挂起，继续执行执行栈中的其他任务,当一个异步事件返回结果后，js会将这个事件加入与当前执行栈不同的另一个队列，我们称之为事件队列。
被放入事件队列不会立刻执行其回调，而是<code>等待当前执行栈中的所有任务都执行完毕， 主线程处于闲置状态时，主线程会去查找事件队列是否有任务</code>。如果有，那么主线程会从中取出排在第一位的事件，并把这个事件对应的回调放入执行栈中，然后执行其中的同步代码...，如此反复，这样就形成了一个无限的循环。这就是这个过程被称为“<code>事件循环（Event Loop）</code>”的原因。
这里还有一张图来展示这个过程:</p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181406260.png" alt="TASKQUEUE"></p> <p>图中的stack表示我们所说的执行栈，web apis则是代表一些异步事件，而callback queue即事件队列。
以上的事件循环过程是一个宏观的表述，实际上因为异步任务之间并不相同，因此他们的执行优先级也有区别。不同的异步任务被分为两类：<code>微任务（micro task）</code>和<code>宏任务（macro task）</code>,此部分看下方详解</p> <p><strong>Ⅲ-宏任务(macro task)与微任务(micro task)</strong></p> <p>宏任务与微任务亦属于<a href="https://gitee.com/hongjilin/hongs-study-notes/tree/master/%E7%BC%96%E7%A8%8B_%E5%89%8D%E7%AB%AF%E5%BC%80%E5%8F%91%E5%AD%A6%E4%B9%A0%E7%AC%94%E8%AE%B0/HTML+CSS+JS%E5%9F%BA%E7%A1%80%E7%AC%94%E8%AE%B0/JavaScript%E7%AC%94%E8%AE%B0#%E2%85%A1-%E6%B5%8F%E8%A7%88%E5%99%A8%E7%8E%AF%E5%A2%83%E4%B8%8BJS%E5%BC%95%E6%93%8E%E7%9A%84%E4%BA%8B%E4%BB%B6%E5%BE%AA%E7%8E%AF%E6%9C%BA%E5%88%B6" target="_blank" rel="noopener noreferrer">Ⅱ-浏览器环境下JS引擎的事件循环机制<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a>内知识点,但本人觉得比较重要,将其提高至其知识点</p> <p><strong>① 宏任务队列与微任务队列解释</strong></p> <p>顾名思义,宏任务放至宏任务队列(简称宏队列)中、微任务放至微任务队列(简称微队列)中</p> <ol><li><p>JS中用来存储待执行回调函数的队列包含2个不同特定的列队</p> <ul><li>宏队列:用来保存待执行的宏任务(回调),比如:定时器回调/ajax回调/dom事件回调</li> <li>微队列:用来保存待执行的微任务(回调),比如:Promise的回调/muntation回调</li></ul></li> <li><p>JS执行时会区别这2个队列:</p> <ul><li>JS执行引擎首先必须执行所有的初始化同步任务代码</li> <li>每次准备取出第一个宏任务执行前,都要将所有的微任务一个一个取出来执行</li></ul></li></ol> <p>前面我们介绍过，在一个事件循环中，异步事件返回结果后会被放到一个任务队列中。然而，根据这个异步事件的类型，这个事件实际上会被对应的宏任务队列或者微任务队列中去。并且在当前执行栈为空的时候，主线程会 查看微任务队列是否有事件存在。如果不存在，那么再去宏任务队列中取出一个事件并把对应的回到加入当前执行栈；如果存在，则会依次执行队列中事件对应的回调，直到微任务队列为空，然后去宏任务队列中取出最前面的一个事件，把对应的回调加入当前执行栈...如此反复，进入循环。
我们只需记住:<strong>当前执行栈执行完毕时会立刻先处理所有微任务队列中的事件，然后再去宏任务队列中取出一个事件。同一次事件循环中，微任务永远在宏任务之前执行</strong></p> <p><strong>② 原理图</strong></p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181409119.png" alt="macrotask"></p> <p><strong>③ 由代码逆向理解宏任务与微任务</strong></p> <div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span> 
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout callback1（）'</span><span class="token punctuation">)</span><span class="token comment">//立即放入宏队列</span>
  Promise<span class="token punctuation">.</span><span class="token function">resolve</span><span class="token punctuation">(</span><span class="token number">3</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">then</span><span class="token punctuation">(</span>
    <span class="token parameter">value</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span> 
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Promise onResolved3()'</span><span class="token punctuation">,</span> value<span class="token punctuation">)</span><span class="token comment">//当这个宏任务执行后 立马放入微队列,所以这个微任务执行完后下个宏任务才能执行 </span>
    <span class="token punctuation">}</span>
  <span class="token punctuation">)</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span>

<span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span> 
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout callback2（）'</span><span class="token punctuation">)</span> <span class="token comment">//立即放入宏队列,</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span>

Promise<span class="token punctuation">.</span><span class="token function">resolve</span><span class="token punctuation">(</span><span class="token number">1</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">then</span><span class="token punctuation">(</span>
  <span class="token parameter">value</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span> 
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Promise onResolved1()'</span><span class="token punctuation">,</span> value<span class="token punctuation">)</span><span class="token comment">//立即放入微队列</span>
    <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout callback3（）'</span><span class="token punctuation">,</span> value<span class="token punctuation">)</span> <span class="token comment">//立即放入宏任务</span>
    <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">)</span>

Promise<span class="token punctuation">.</span><span class="token function">resolve</span><span class="token punctuation">(</span><span class="token number">2</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">then</span><span class="token punctuation">(</span>
  <span class="token parameter">value</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span> 
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'Promise onResolved2()'</span><span class="token punctuation">,</span> value<span class="token punctuation">)</span><span class="token comment">//立即放入微队列</span>
  <span class="token punctuation">}</span>
<span class="token punctuation">)</span>
console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'同步代码'</span><span class="token punctuation">)</span> <span class="token comment">//同步代码立即执行</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br><span class="line-number">25</span><br><span class="line-number">26</span><br><span class="line-number">27</span><br><span class="line-number">28</span><br></div></div><div class="language-JavaScript line-numbers-mode"><pre class="language-javascript"><code><span class="token string">'同步代码'</span><span class="token punctuation">,</span>
  <span class="token string">'Promise onResolved1()'</span><span class="token punctuation">,</span>
  <span class="token string">'Promise onResolved2()'</span><span class="token punctuation">,</span>
  <span class="token string">'timeout callback1（）'</span><span class="token punctuation">,</span>
  <span class="token string">'Promise onResolved3()'</span><span class="token punctuation">,</span>
  <span class="token string">'timeout callback2（）'</span><span class="token punctuation">,</span>
  <span class="token string">'timeout callback3（）'</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><p><strong>Ⅳ-node环境下的事件循环机制</strong></p> <p>不学node的小伙伴就跳过此部分直接去下一节Web Workers笔记吧</p> <p><strong>① 与浏览器环境有何不同?</strong></p> <p>在node中，事件循环表现出的状态与浏览器中大致相同。不同的是node中有一套自己的模型。node中事件循环的实现是依靠的libuv引擎。我们知道node选择chrome v8引擎作为js解释器，v8引擎将js代码分析后去调用对应的node api，而这些api最后则由libuv引擎驱动，执行对应的任务，并把不同的事件放在不同的队列中等待主线程执行。·<code>因此实际上node中的事件循环存在于libuv引擎中。</code></p> <p><strong>② 事件循环模型</strong></p> <p>下面是一个libuv引擎中的事件循环的模型</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token comment">//libuv引擎中的事件循环的模型</span>
   ┌───────────────────────┐
┌─<span class="token operator">&gt;</span>│        timers         │
│  └──────────┬────────────┘
│  ┌──────────┴────────────┐
│  │     <span class="token constant">I</span><span class="token operator">/</span><span class="token constant">O</span> callbacks     │
│  └──────────┬────────────┘
│  ┌──────────┴────────────┐
│  │     idle<span class="token punctuation">,</span> prepare     │
│  └──────────┬────────────┘      ┌───────────────┐
│  ┌──────────┴────────────┐      │   incoming<span class="token operator">:</span>   │
│  │         poll          │<span class="token operator">&lt;</span>──connections───     │
│  └──────────┬────────────┘      │   data<span class="token punctuation">,</span> etc<span class="token punctuation">.</span>  │
│  ┌──────────┴────────────┐      └───────────────┘
│  │        check          │
│  └──────────┬────────────┘
│  ┌──────────┴────────────┐
└──┤    close callbacks    │
   └───────────────────────┘
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br></div></div><p><em>注：模型中的每一个方块代表事件循环的一个阶段</em>
这个模型是node官网上的一篇文章中给出的，我下面的解释也都来源于这篇文章。我会在文末把文章地址贴出来，有兴趣的朋友可以亲自与看看原文。</p> <p><strong>③ 事件循环各阶段详解</strong></p> <p>从上面这个模型中，我们可以大致分析出node中的事件循环的顺序：
外部输入数据--&gt;轮询阶段(poll)--&gt;检查阶段(check)--&gt;关闭事件回调阶段(close callback)--&gt;定时器检测阶段(timer)--&gt;I/O事件回调阶段(I/O callbacks)--&gt;闲置阶段(idle, prepare)--&gt;轮询阶段...
这些阶段大致的功能如下：</p> <ul><li>timers(定时器检测阶段): 这个阶段执行定时器队列中的回调如 setTimeout() 和 setInterval()。</li> <li>I/O callbacks(I/O事件回调阶段): 这个阶段执行几乎所有的回调。但是不包括close事件，定时器和setImmediate()的回调。</li> <li>idle, prepare: 这个阶段仅在内部使用，可以不必理会。</li> <li>poll(轮询阶段): 等待新的I/O事件，node在一些特殊情况下会阻塞在这里。</li> <li>check(检查阶段): setImmediate()的回调会在这个阶段执行。</li> <li>close callbacks(关闭事件回调阶段): 例如socket.on('close', ...)这种close事件的回调。</li></ul> <p>下面我们来按照代码第一次进入libuv引擎后的顺序来详细解说这些阶段：</p> <p><strong>poll(轮询阶段)</strong></p> <p>当个v8引擎将js代码解析后传入libuv引擎后，循环首先进入poll阶段。poll阶段的执行逻辑如下： 先查看poll queue中是否有事件，有任务就按先进先出的顺序依次执行回调。 当queue为空时，会检查是否有setImmediate()的callback，如果有就进入check阶段执行这些callback。但同时也会检查是否有到期的timer，如果有，就把这些到期的timer的callback按照调用顺序放到timer queue中，之后循环会进入timer阶段执行queue中的 callback。 这两者的顺序是不固定的，收到代码运行的环境的影响。如果两者的queue都是空的，那么loop会在poll阶段停留，直到有一个i/o事件返回，循环会进入i/o callback阶段并立即执行这个事件的callback。
值得注意的是，poll阶段在执行poll queue中的回调时实际上不会无限的执行下去。<code>有两种情况poll阶段会终止执行poll queue中的下一个回调：1.所有回调执行完毕。2.执行数超过了node的限制。</code></p> <p><strong>check(检查阶段)</strong></p> <p>check阶段专门用来执行setImmediate()方法的回调，当poll阶段进入空闲状态，并且setImmediate queue中有callback时，事件循环进入这个阶段。</p> <p><strong>close callbacks(关闭事件回调阶段)</strong></p> <p>当一个socket连接或者一个handle被突然关闭时（例如调用了socket.destroy()方法），close事件会被发送到这个阶段执行回调。否则事件会用process.nextTick（）方法发送出去。</p> <p><strong>timers(定时器检测阶段)</strong></p> <p>这个阶段以先进先出的方式执行所有到期的timer加入timer队列里的callback，一个timer callback指得是一个通过setTimeout或者setInterval函数设置的回调函数。</p> <p><strong>I/O callbacks(I/O事件回调阶段)</strong></p> <p>如上文所言，这个阶段主要执行大部分I/O事件的回调，包括一些为操作系统执行的回调。例如一个TCP连接生错误时，系统需要执行回调来获得这个错误的报告。</p> <p><strong>④ process.nextTick,setTimeout与setImmediate的区别与使用场景</strong></p> <p>在node中有三个常用的用来推迟任务执行的方法：process.nextTick,setTimeout（setInterval与之相同）与setImmediate
这三者间存在着一些非常不同的区别：</p> <p><strong>process.nextTick()</strong></p> <p>尽管没有提及，但是实际上node中存在着一个特殊的队列，即nextTick queue。这个队列中的回调执行虽然没有被表示为一个阶段，当时这些事件却会在每一个阶段执行完毕准备进入下一个阶段时优先执行。当事件循环准备进入下一个阶段之前，会先检查nextTick queue中是否有任务，如果有，那么会先清空这个队列。与执行poll queue中的任务不同的是，这个操作在队列清空前是不会停止的。这也就意味着，错误的使用<code>process.nextTick()</code>方法会导致node进入一个死循环。。直到内存泄漏。
使用这个方法比较合适呢？下面有一个例子：</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token keyword">const</span> server <span class="token operator">=</span> net<span class="token punctuation">.</span><span class="token function">createServer</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function">listen</span><span class="token punctuation">(</span><span class="token number">8080</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
server<span class="token punctuation">.</span><span class="token function">on</span><span class="token punctuation">(</span><span class="token string">'listening'</span><span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span><span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br></div></div><p>这个例子中当，当listen方法被调用时，除非端口被占用，否则会立刻绑定在对应的端口上。这意味着此时这个端口可以立刻触发listening事件并执行其回调。然而，这时候on('listening)还没有将callback设置好，自然没有callback可以执行。为了避免出现这种情况，node会在listen事件中使用process.nextTick()方法，确保事件在回调函数绑定后被触发。</p> <p><strong>setTimeout()和setImmediate()</strong></p> <p>在三个方法中，这两个方法最容易被弄混。实际上，某些情况下这两个方法的表现也非常相似。然而实际上，这两个方法的意义却大为不同。
setTimeout()方法是定义一个回调，并且希望这个回调在我们所指定的时间间隔后第一时间去执行。注意这个“第一时间执行”，这意味着，受到操作系统和当前执行任务的诸多影响，该回调并不会在我们预期的时间间隔后精准的执行。执行的时间存在一定的延迟和误差，这是不可避免的。node会在可以执行timer回调的第一时间去执行你所设定的任务。
setImmediate()方法从意义上将是立刻执行的意思，但是实际上它却是在一个固定的阶段才会执行回调，即poll阶段之后。有趣的是，这个名字的意义和之前提到过的process.nextTick()方法才是最匹配的。node的开发者们也清楚这两个方法的命名上存在一定的混淆，他们表示不会把这两个方法的名字调换过来---因为有大量的node程序使用着这两个方法，调换命名所带来的好处与它的影响相比不值一提。
setTimeout()和不设置时间间隔的setImmediate()表现上及其相似。猜猜下面这段代码的结果是什么？</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code><span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
   console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

<span class="token function">setImmediate</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
   console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'immediate'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br></div></div><p>实际上，答案是不一定。没错，就连node的开发者都无法准确的判断这两者的顺序谁前谁后。这取决于这段代码的运行环境。运行环境中的各种复杂的情况会导致在同步队列里两个方法的顺序随机决定。但是，在一种情况下可以准确判断两个方法回调的执行顺序，那就是在一个I/O事件的回调中。下面这段代码的顺序永远是固定的：</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token keyword">const</span> fs <span class="token operator">=</span> <span class="token function">require</span><span class="token punctuation">(</span><span class="token string">'fs'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

fs<span class="token punctuation">.</span><span class="token function">readFile</span><span class="token punctuation">(</span>__filename<span class="token punctuation">,</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
  <span class="token function">setTimeout</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'timeout'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span><span class="token punctuation">,</span> <span class="token number">0</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token function">setImmediate</span><span class="token punctuation">(</span><span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token operator">=&gt;</span> <span class="token punctuation">{</span>
    console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'immediate'</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
  <span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">;</span>
<span class="token punctuation">}</span><span class="token punctuation">)</span><span class="token punctuation">;</span>

</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br></div></div><p>答案永远是：</p> <div class="language- line-numbers-mode"><pre class="language-text"><code>immediate
timeout
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br></div></div><p>因为在I/O事件的回调中，setImmediate方法的回调永远在timer的回调前执行。</p> <h2 id="_5-web-workers"><a href="#_5-web-workers" class="header-anchor">#</a> 5 Web Workers</h2> <p>想了解更多可以点击链接查看更多,此处只是大致了解学习 --&gt;<a href="https://gitee.com/link?target=https%3A%2F%2Fdeveloper.mozilla.org%2Fzh-CN%2Fdocs%2FWeb%2FAPI%2FWeb_Workers_API%2FUsing_web_workers" target="_blank" rel="noopener noreferrer">Web Workers<span><svg xmlns="http://www.w3.org/2000/svg" aria-hidden="true" focusable="false" x="0px" y="0px" viewBox="0 0 100 100" width="15" height="15" class="icon outbound"><path fill="currentColor" d="M18.8,85.1h56l0,0c2.2,0,4-1.8,4-4v-32h-8v28h-48v-48h28v-8h-32l0,0c-2.2,0-4,1.8-4,4v56C14.8,83.3,16.6,85.1,18.8,85.1z"></path> <polygon fill="currentColor" points="45.7,48.7 51.3,54.3 77.2,28.5 77.2,37.2 85.2,37.2 85.2,14.9 62.8,14.9 62.8,22.9 71.5,22.9"></polygon></svg> <span class="sr-only">(opens new window)</span></span></a></p> <ol><li>H5规范提供了js分线程的实现, 取名为: Web Workers</li> <li>相关API
<ul><li>Worker: 构造函数, 加载分线程执行的js文件</li> <li>Worker.prototype.onmessage: 用于接收另一个线程的回调函数</li> <li>Worker.prototype.postMessage: 向另一个线程发送消息</li></ul></li> <li>不足
<ul><li>worker内代码不能操作DOM(更新UI)</li> <li>不能跨域加载JS</li> <li>不是每个浏览器都支持这个新特性</li></ul></li></ol> <p><strong>Ⅰ-抛砖引玉,引出用处</strong></p> <p>还是拿斐波那契（Fibonacci）数列来做例子,这东西效率低,可以拿来模拟</p> <div class="language-html line-numbers-mode"><pre class="language-html"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>body</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>input</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text<span class="token punctuation">&quot;</span></span> <span class="token attr-name">placeholder</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>数值<span class="token punctuation">&quot;</span></span> <span class="token attr-name">id</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>number<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span> <span class="token attr-name">id</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>btn<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>计算<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text/javascript<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
    <span class="token comment">// 1 1 2 3 5 8    f(n) = f(n-1) + f(n-2)</span>
    <span class="token keyword">function</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span><span class="token parameter">n</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">return</span> n<span class="token operator">&lt;=</span><span class="token number">2</span> <span class="token operator">?</span> <span class="token number">1</span> <span class="token operator">:</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>n<span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">)</span> <span class="token operator">+</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>n<span class="token operator">-</span><span class="token number">2</span><span class="token punctuation">)</span>  <span class="token comment">//递归调用</span>
    <span class="token punctuation">}</span>
    <span class="token comment">// console.log(fibonacci(7))</span>
    <span class="token keyword">var</span> input <span class="token operator">=</span> document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'number'</span><span class="token punctuation">)</span>
    document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'btn'</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">var</span> number <span class="token operator">=</span> input<span class="token punctuation">.</span>value
      <span class="token keyword">var</span> result <span class="token operator">=</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>number<span class="token punctuation">)</span>
      <span class="token function">alert</span><span class="token punctuation">(</span>result<span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
  </span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br></div></div><p>当我运行此行代码,传入计算数值为50左右(有的甚至更低),整个页面就会卡住好久的时间不能操作(计算结束后才会弹窗,但是未弹窗的这段时间用户并不能进行操作),这时候就会发现单线程的弊端了</p> <p><strong>Ⅱ-尝试使用</strong></p> <p><strong>① 主线程</strong></p> <ol><li>创建一个Worker对象</li> <li>绑定[主线程接收分线程返回的数据]方法</li> <li>主线程向分线程发送数据,然后等待接受数据</li> <li>接收到分线程回馈的数据,将数据进行处理(如弹窗)</li></ol> <div class="language-html line-numbers-mode"><pre class="language-html"><code><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>body</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>input</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text<span class="token punctuation">&quot;</span></span> <span class="token attr-name">placeholder</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>数值<span class="token punctuation">&quot;</span></span> <span class="token attr-name">id</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>number<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>button</span> <span class="token attr-name">id</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>btn<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span>计算<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>button</span><span class="token punctuation">&gt;</span></span>
  <span class="token tag"><span class="token tag"><span class="token punctuation">&lt;</span>script</span> <span class="token attr-name">type</span><span class="token attr-value"><span class="token punctuation attr-equals">=</span><span class="token punctuation">&quot;</span>text/javascript<span class="token punctuation">&quot;</span></span><span class="token punctuation">&gt;</span></span><span class="token script"><span class="token language-javascript">
    <span class="token keyword">var</span> input <span class="token operator">=</span> document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'number'</span><span class="token punctuation">)</span>
    document<span class="token punctuation">.</span><span class="token function">getElementById</span><span class="token punctuation">(</span><span class="token string">'btn'</span><span class="token punctuation">)</span><span class="token punctuation">.</span><span class="token function-variable function">onclick</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
      <span class="token keyword">var</span> number <span class="token operator">=</span> input<span class="token punctuation">.</span>value

      <span class="token comment">//创建一个Worker对象</span>
      <span class="token keyword">var</span> worker <span class="token operator">=</span> <span class="token keyword">new</span> <span class="token class-name">Worker</span><span class="token punctuation">(</span><span class="token string">'worker.js'</span><span class="token punctuation">)</span>
      <span class="token comment">// 绑定接收消息的监听</span>
      worker<span class="token punctuation">.</span><span class="token function-variable function">onmessage</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">event</span><span class="token punctuation">)</span> <span class="token punctuation">{</span> <span class="token comment">//此处变成回调代码,会在初始化工作完成后才会进行</span>
        console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'主线程接收分线程返回的数据: '</span><span class="token operator">+</span>event<span class="token punctuation">.</span>data<span class="token punctuation">)</span>
        <span class="token function">alert</span><span class="token punctuation">(</span>event<span class="token punctuation">.</span>data<span class="token punctuation">)</span>
      <span class="token punctuation">}</span>

      <span class="token comment">// 向分线程发送消息</span>
      worker<span class="token punctuation">.</span><span class="token function">postMessage</span><span class="token punctuation">(</span>number<span class="token punctuation">)</span>
      console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'主线程向分线程发送数据: '</span><span class="token operator">+</span>number<span class="token punctuation">)</span>
    <span class="token punctuation">}</span>
    <span class="token comment">// console.log(this) // window</span>

  </span></span><span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>script</span><span class="token punctuation">&gt;</span></span>
<span class="token tag"><span class="token tag"><span class="token punctuation">&lt;/</span>body</span><span class="token punctuation">&gt;</span></span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br><span class="line-number">18</span><br><span class="line-number">19</span><br><span class="line-number">20</span><br><span class="line-number">21</span><br><span class="line-number">22</span><br><span class="line-number">23</span><br><span class="line-number">24</span><br></div></div><p><strong>② 分线程</strong></p> <p>将计算放置分线程中
注意:alert(result) alert是window的方法, 在分线程不能调用,分线程中的全局对象不再是window, 所以在分线程中不可能更新界面</p> <div class="language-javascript line-numbers-mode"><pre class="language-javascript"><code>
<span class="token comment">//worker.js</span>
<span class="token keyword">function</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span><span class="token parameter">n</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">return</span> n<span class="token operator">&lt;=</span><span class="token number">2</span> <span class="token operator">?</span> <span class="token number">1</span> <span class="token operator">:</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>n<span class="token operator">-</span><span class="token number">1</span><span class="token punctuation">)</span> <span class="token operator">+</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>n<span class="token operator">-</span><span class="token number">2</span><span class="token punctuation">)</span>  <span class="token comment">//递归调用</span>
<span class="token punctuation">}</span>

console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token keyword">this</span><span class="token punctuation">)</span>
<span class="token keyword">this</span><span class="token punctuation">.</span><span class="token function-variable function">onmessage</span> <span class="token operator">=</span> <span class="token keyword">function</span> <span class="token punctuation">(</span><span class="token parameter">event</span><span class="token punctuation">)</span> <span class="token punctuation">{</span>
  <span class="token keyword">var</span> number <span class="token operator">=</span> event<span class="token punctuation">.</span>data
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'分线程接收到主线程发送的数据: '</span><span class="token operator">+</span>number<span class="token punctuation">)</span>
  <span class="token comment">//计算</span>
  <span class="token keyword">var</span> result <span class="token operator">=</span> <span class="token function">fibonacci</span><span class="token punctuation">(</span>number<span class="token punctuation">)</span>
  <span class="token function">postMessage</span><span class="token punctuation">(</span>result<span class="token punctuation">)</span>
  console<span class="token punctuation">.</span><span class="token function">log</span><span class="token punctuation">(</span><span class="token string">'分线程向主线程返回数据: '</span><span class="token operator">+</span>result<span class="token punctuation">)</span>
  <span class="token comment">// alert(result)  alert是window的方法, 在分线程不能调用</span>
  <span class="token comment">// 分线程中的全局对象不再是window, 所以在分线程中不可能更新界面</span>
<span class="token punctuation">}</span>
</code></pre> <div class="line-numbers-wrapper"><span class="line-number">1</span><br><span class="line-number">2</span><br><span class="line-number">3</span><br><span class="line-number">4</span><br><span class="line-number">5</span><br><span class="line-number">6</span><br><span class="line-number">7</span><br><span class="line-number">8</span><br><span class="line-number">9</span><br><span class="line-number">10</span><br><span class="line-number">11</span><br><span class="line-number">12</span><br><span class="line-number">13</span><br><span class="line-number">14</span><br><span class="line-number">15</span><br><span class="line-number">16</span><br><span class="line-number">17</span><br></div></div><p><strong>Ⅲ-流程原理图</strong></p> <p><img src="https://hasakwebblogimg.oss-cn-hangzhou.aliyuncs.com/202211181419599.png" alt="liucheng"></p></div></section> <footer class="page-edit"><!----> <!----></footer> <div class="page-nav"><p class="inner"><span class="prev"><a href="/blogs/基础/js/20221114js05.html" class="prev">
          1-5 内置对象 简单类型与复杂类型
        </a></span> <span class="next"><a href="/blogs/基础/js/20221114js07.html">
          2-1 Web APIs 简介 DOM
        </a></span></p></div> <div class="comments-wrapper"><!----></div></main></div> <!----></div> <ul class="sub-sidebar sub-sidebar-wrapper" style="width:0;" data-v-b57cc07c data-v-7dd95ae2></ul></div></div></div><div class="global-ui"><div class="back-to-ceiling" style="right:1rem;bottom:6rem;width:2.5rem;height:2.5rem;border-radius:.25rem;line-height:2.5rem;display:none;" data-v-c6073ba8 data-v-c6073ba8><svg t="1574745035067" viewBox="0 0 1024 1024" version="1.1" xmlns="http://www.w3.org/2000/svg" p-id="5404" class="icon" data-v-c6073ba8><path d="M526.60727968 10.90185116a27.675 27.675 0 0 0-29.21455937 0c-131.36607665 82.28402758-218.69155461 228.01873535-218.69155402 394.07834331a462.20625001 462.20625001 0 0 0 5.36959153 69.94390903c1.00431239 6.55289093-0.34802892 13.13561351-3.76865779 18.80351572-32.63518765 54.11355614-51.75690182 118.55860487-51.7569018 187.94566865a371.06718723 371.06718723 0 0 0 11.50484808 91.98906777c6.53300375 25.50556257 41.68394495 28.14064038 52.69160883 4.22606766 17.37162448-37.73630017 42.14135425-72.50938081 72.80769204-103.21549295 2.18761121 3.04276886 4.15646224 6.24463696 6.40373557 9.22774369a1871.4375 1871.4375 0 0 0 140.04691725 5.34970492 1866.36093723 1866.36093723 0 0 0 140.04691723-5.34970492c2.24727335-2.98310674 4.21612437-6.18497483 6.3937923-9.2178004 30.66633723 30.70611158 55.4360664 65.4791928 72.80769147 103.21549355 11.00766384 23.91457269 46.15860503 21.27949489 52.69160879-4.22606768a371.15156223 371.15156223 0 0 0 11.514792-91.99901164c0-69.36717486-19.13165746-133.82216804-51.75690182-187.92578088-3.42062944-5.66790279-4.76302748-12.26056868-3.76865837-18.80351632a462.20625001 462.20625001 0 0 0 5.36959269-69.943909c-0.00994388-166.08943902-87.32547796-311.81420293-218.6915546-394.09823051zM605.93803103 357.87693858a93.93749974 93.93749974 0 1 1-187.89594924 6.1e-7 93.93749974 93.93749974 0 0 1 187.89594924-6.1e-7z" p-id="5405" data-v-c6073ba8></path><path d="M429.50777625 765.63860547C429.50777625 803.39355007 466.44236686 1000.39046097 512.00932183 1000.39046097c45.56695499 0 82.4922232-197.00623328 82.5015456-234.7518555 0-37.75494459-36.9345906-68.35043303-82.4922232-68.34111062-45.57627738-0.00932239-82.52019037 30.59548842-82.51086798 68.34111062z" p-id="5406" data-v-c6073ba8></path></svg></div></div></div>
    <script src="/assets/js/app.c7915c77.js" defer></script><script src="/assets/js/3.f80332a6.js" defer></script><script src="/assets/js/1.5cffa4a1.js" defer></script><script src="/assets/js/32.098b21df.js" defer></script>
  </body>
</html>
